1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * Copyright (C) ASPEED Technology Inc.
4  *
5  */
6 
7 #include <common.h>
8 #include <clk.h>
9 #include <dm.h>
10 #include <errno.h>
11 #include <ram.h>
12 #include <regmap.h>
13 #include <reset.h>
14 #include <asm/io.h>
15 #include <asm/arch/scu_ast2600.h>
16 #include <asm/arch/sdram_ast2600.h>
17 #include <linux/err.h>
18 #include <linux/kernel.h>
19 #include <dt-bindings/clock/ast2600-clock.h>
20 #include "sdram_phy_ast2600.h"
21 
22 /* in order to speed up DRAM init time, write pre-defined values to registers
23  * directly */
24 #define AST2600_SDRAMMC_MANUAL_CLK
25 
26 /* register offset */
27 #define AST_SCU_FPGA_STATUS	0x004
28 #define AST_SCU_HANDSHAKE	0x100
29 #define AST_SCU_MPLL		0x220
30 #define AST_SCU_MPLL_EXT	0x224
31 #define AST_SCU_FPGA_PLL	0x400
32 #define AST_SCU_HW_STRAP	0x500
33 
34 
35 /* bit-field of AST_SCU_HW_STRAP */
36 #define SCU_HWSTRAP_VGAMEM_SHIFT	13
37 #define SCU_HWSTRAP_VGAMEM_MASK		GENMASK(14, 13)
38 
39 
40 /* bit-field of AST_SCU_HANDSHAKE */
41 #define SCU_SDRAM_INIT_READY_MASK	BIT(6)
42 #define SCU_SDRAM_INIT_BY_SOC_MASK	BIT(7)
43 
44 /* bit-field of AST_SCU_MPLL */
45 #define SCU_MPLL_RESET			BIT(25)
46 #define SCU_MPLL_BYPASS			BIT(24)
47 #define SCU_MPLL_TURN_OFF		BIT(23)
48 #define SCU_MPLL_FREQ_MASK		GENMASK(22, 0)
49 
50 #define SCU_MPLL_FREQ_400M		0x0008405F
51 #define SCU_MPLL_EXT_400M		0x00000031
52 //#define SCU_MPLL_FREQ_400M		0x0038007F
53 //#define SCU_MPLL_EXT_400M		0x0000003F
54 #define SCU_MPLL_FREQ_200M		0x0078007F
55 #define SCU_MPLL_EXT_200M		0x0000003F
56 #define SCU_MPLL_FREQ_100M		0x0078003F
57 #define SCU_MPLL_EXT_100M		0x0000001F
58 /* MPLL configuration */
59 #if defined(CONFIG_ASPEED_DDR4_1600)
60 #define SCU_MPLL_FREQ_CFG		SCU_MPLL_FREQ_400M
61 #define SCU_MPLL_EXT_CFG		SCU_MPLL_EXT_400M
62 #elif defined(CONFIG_ASPEED_DDR4_800)
63 #define SCU_MPLL_FREQ_CFG		SCU_MPLL_FREQ_200M
64 #define SCU_MPLL_EXT_CFG		SCU_MPLL_EXT_200M
65 #elif defined(CONFIG_ASPEED_DDR4_400)
66 #define SCU_MPLL_FREQ_CFG		SCU_MPLL_FREQ_100M
67 #define SCU_MPLL_EXT_CFG		SCU_MPLL_EXT_100M
68 #else
69 #error "undefined DDR4 target rate\n"
70 #endif
71 
72 /* AC timing and SDRAM mode registers */
73 #if defined(CONFIG_FPGA_ASPEED) || defined(CONFIG_ASPEED_PALLADIUM)
74 /* mode register settings for FPGA are fixed */
75 #define DDR4_MR01_MODE		0x03010100
76 #define DDR4_MR23_MODE		0x00000000
77 #define DDR4_MR45_MODE		0x04C00000
78 #define DDR4_MR6_MODE		0x00000050
79 #define DDR4_TRFC_FPGA		0x17263434
80 
81 /* FPGA need for an additional initialization procedure: search read window */
82 #define SEARCH_RDWIN_ANCHOR_0   (CONFIG_SYS_SDRAM_BASE + 0x0000)
83 #define SEARCH_RDWIN_ANCHOR_1   (CONFIG_SYS_SDRAM_BASE + 0x0004)
84 #define SEARCH_RDWIN_PTRN_0     0x12345678
85 #define SEARCH_RDWIN_PTRN_1     0xaabbccdd
86 #define SEARCH_RDWIN_PTRN_SUM   0xbcf02355
87 #else
88 /* mode register setting for real chip are derived from the model GDDR4-1600 */
89 #define DDR4_MR01_MODE		0x03010510
90 #define DDR4_MR23_MODE		0x00000000
91 #define DDR4_MR45_MODE		0x04000000
92 #define DDR4_MR6_MODE           0x00000400
93 #define DDR4_TRFC_1600		0x467299f1
94 #define DDR4_TRFC_800		0x23394c78
95 #define DDR4_TRFC_400		0x111c263c
96 #endif /* end of "#if defined(CONFIG_FPGA_ASPEED) ||                           \
97 	  defined(CONFIG_ASPEED_PALLADIUM)" */
98 
99 #if defined(CONFIG_FPGA_ASPEED) || defined(CONFIG_ASPEED_PALLADIUM)
100 #define DDR4_TRFC			DDR4_TRFC_FPGA
101 #else
102 /* real chip setting */
103 #if defined(CONFIG_ASPEED_DDR4_1600)
104 #define DDR4_TRFC			DDR4_TRFC_1600
105 #define DDR4_PHY_TRAIN_TRFC		0xc30
106 #elif defined(CONFIG_ASPEED_DDR4_800)
107 #define DDR4_TRFC			DDR4_TRFC_800
108 #define DDR4_PHY_TRAIN_TRFC		0x618
109 #elif defined(CONFIG_ASPEED_DDR4_400)
110 #define DDR4_TRFC			DDR4_TRFC_400
111 #define DDR4_PHY_TRAIN_TRFC		0x30c
112 #else
113 #error "undefined tRFC setting"
114 #endif	/* end of "#if (SCU_MPLL_FREQ_CFG == SCU_MPLL_FREQ_400M)" */
115 #endif  /* end of "#if defined(CONFIG_FPGA_ASPEED) ||                          \
116 	   defined(CONFIG_ASPEED_PALLADIUM)" */
117 
118 /* supported SDRAM size */
119 #define SDRAM_SIZE_1KB		(1024U)
120 #define SDRAM_SIZE_1MB		(SDRAM_SIZE_1KB * SDRAM_SIZE_1KB)
121 #define SDRAM_MIN_SIZE		(256 * SDRAM_SIZE_1MB)
122 #define SDRAM_MAX_SIZE		(2048 * SDRAM_SIZE_1MB)
123 
124 
125 DECLARE_GLOBAL_DATA_PTR;
126 
127 /*
128  * Bandwidth configuration parameters for different SDRAM requests.
129  * These are hardcoded settings taken from Aspeed SDK.
130  */
131 #if defined(CONFIG_FPGA_ASPEED) || defined(CONFIG_ASPEED_PALLADIUM)
132 static const u32 ddr4_ac_timing[4] = {0x030C0207, 0x04451133, 0x0E010200,
133                                       0x00000140};
134 
135 static const u32 ddr_max_grant_params[4] = {0x88888888, 0x88888888, 0x88888888,
136                                             0x88888888};
137 #else
138 static const u32 ddr4_ac_timing[4] = {0x040e0307, 0x0f4711f1, 0x0e060304,
139                                       0x00001240};
140 
141 static const u32 ddr_max_grant_params[4] = {0x44444444, 0x44444444, 0x44444444,
142                                             0x44444444};
143 #endif
144 
145 struct dram_info {
146 	struct ram_info info;
147 	struct clk ddr_clk;
148 	struct ast2600_sdrammc_regs *regs;
149 	void __iomem *scu;
150 	struct ast2600_ddr_phy *phy;
151 	void __iomem *phy_setting;
152 	void __iomem *phy_status;
153 	ulong clock_rate;
154 };
155 
156 static void ast2600_sdramphy_kick_training(struct dram_info *info)
157 {
158 #if !defined(CONFIG_FPGA_ASPEED) && !defined(CONFIG_ASPEED_PALLADIUM)
159         struct ast2600_sdrammc_regs *regs = info->regs;
160         u32 volatile data;
161 
162         writel(SDRAM_PHYCTRL0_NRST, &regs->phy_ctrl[0]);
163 	udelay(5);
164         writel(SDRAM_PHYCTRL0_NRST | SDRAM_PHYCTRL0_INIT, &regs->phy_ctrl[0]);
165 	udelay(1000);
166 
167 	while (1) {
168 		data = readl(&regs->phy_ctrl[0]) & SDRAM_PHYCTRL0_INIT;
169 		if (~data) {
170 			break;
171 		}
172 	}
173 
174 #if 0
175 	while (1) {
176 		data = readl(0x1e6e0400) & BIT(1);
177 		if (data) {
178 			break;
179 		}
180 	}
181 #endif
182 #endif
183 }
184 
185 /**
186  * @brief	load DDR-PHY configurations table to the PHY registers
187  * @param[in]	p_tbl - pointer to the configuration table
188  * @param[in]	info - pointer to the DRAM info struct
189  *
190  * There are two sets of MRS (Mode Registers) configuration in ast2600 memory
191  * system: one is in the SDRAM MC (memory controller) which is used in run
192  * time, and the other is in the DDR-PHY IP which is used during DDR-PHY
193  * training.
194 */
195 static void ast2600_sdramphy_init(u32 *p_tbl, struct dram_info *info)
196 {
197 #if !defined(CONFIG_FPGA_ASPEED) && !defined(CONFIG_ASPEED_PALLADIUM)
198 	u32 reg_base = (u32)info->phy_setting;
199 	u32 addr = p_tbl[0];
200         u32 data;
201         int i = 1;
202 
203 	writel(0, &info->regs->phy_ctrl[0]);
204 	udelay(10);
205 	//writel(SDRAM_PHYCTRL0_NRST, &regs->phy_ctrl[0]);
206 
207 	debug("%s:reg base = 0x%08x, 1st addr = 0x%08x\n", __func__, reg_base,
208                addr);
209 
210         /* load PHY configuration table into PHY-setting registers */
211         while (1) {
212                 if (addr < reg_base) {
213                         debug("invalid DDR-PHY addr: 0x%08x\n", addr);
214                         break;
215                 }
216                 data = p_tbl[i++];
217 
218                 if (DDR_PHY_TBL_END == data) {
219                         break;
220                 } else if (DDR_PHY_TBL_CHG_ADDR == data) {
221                         addr = p_tbl[i++];
222                 } else {
223                         writel(data, addr);
224                         addr += 4;
225                 }
226         }
227 
228 	data = readl(info->phy_setting + 0x84) & ~GENMASK(16, 0);
229 	data |= DDR4_PHY_TRAIN_TRFC;
230 	writel(data, info->phy_setting + 0x84);
231 #endif
232 }
233 
234 static int ast2600_sdramphy_check_status(struct dram_info *info)
235 {
236 #if !defined(CONFIG_FPGA_ASPEED) && !defined(CONFIG_ASPEED_PALLADIUM)
237         u32 value, tmp;
238         u32 reg_base = (u32)info->phy_status;
239 	int need_retrain = 0;
240 
241 	debug("\nSDRAM PHY training report:\n");
242 	/* training status */
243         value = readl(reg_base + 0x00);
244 	debug("rO_DDRPHY_reg offset 0x00 = 0x%08x\n", value);
245         if (value & BIT(3)) {
246                 debug("\tinitial PVT calibration fail\n");
247         }
248         if (value & BIT(5)) {
249                 debug("\truntime calibration fail\n");
250         }
251 
252 	/* PU & PD */
253 	value = readl(reg_base + 0x30);
254 	debug("rO_DDRPHY_reg offset 0x30 = 0x%08x\n", value);
255         debug("  PU = 0x%02x\n", value & 0xff);
256         debug("  PD = 0x%02x\n", (value >> 16) & 0xff);
257 
258 	/* read eye window */
259         value = readl(reg_base + 0x68);
260 	if (0 == (value & GENMASK(7, 0))) {
261 		need_retrain = 1;
262 	}
263 
264 	debug("rO_DDRPHY_reg offset 0x68 = 0x%08x\n", value);
265 	debug("  rising edge of read data eye training pass window\n");
266 	tmp = (((value & GENMASK(7, 0)) >> 0) * 100) / 255;
267 	debug("    B0:%d%%\n", tmp);
268 	tmp = (((value & GENMASK(15, 8)) >> 8) * 100) / 255;
269         debug("    B1:%d%%\n", tmp);
270 
271 	value = readl(reg_base + 0xC8);
272 	debug("rO_DDRPHY_reg offset 0xC8 = 0x%08x\n", value);
273 	debug("  falling edge of read data eye training pass window\n");
274 	tmp = (((value & GENMASK(7, 0)) >> 0) * 100) / 255;
275 	debug("    B0:%d%%\n", tmp);
276 	tmp = (((value & GENMASK(15, 8)) >> 8) * 100) / 255;
277         debug("    B1:%d%%\n", tmp);
278 
279         /* write eye window */
280         value = readl(reg_base + 0x7c);
281 	if (0 == (value & GENMASK(7, 0))) {
282 		need_retrain = 1;
283 	}
284 
285 	debug("rO_DDRPHY_reg offset 0x7C = 0x%08x\n", value);
286 	debug("  rising edge of write data eye training pass window\n");
287 	tmp = (((value & GENMASK(7, 0)) >> 0) * 100) / 255;
288 	debug("    B0:%d%%\n", tmp);
289 	tmp = (((value & GENMASK(15, 8)) >> 8) * 100) / 255;
290         debug("    B1:%d%%\n", tmp);
291 
292 	/* read Vref training result */
293         value = readl(reg_base + 0x88);
294 	debug("rO_DDRPHY_reg offset 0x88 = 0x%08x\n", value);
295         debug("  read Vref training result\n");
296 	tmp = (((value & GENMASK(7, 0)) >> 0) * 100) / 127;
297 	debug("    B0:%d%%\n", tmp);
298 	tmp = (((value & GENMASK(15, 8)) >> 8) * 100) / 127;
299         debug("    B1:%d%%\n", tmp);
300 
301         /* write Vref training result */
302         value = readl(reg_base + 0x90);
303 	debug("rO_DDRPHY_reg offset 0x90 = 0x%08x\n", value);
304 	tmp = (((value & GENMASK(5, 0)) >> 0) * 100) / 127;
305         debug("  write Vref training result = %d%%\n", tmp);
306 
307         /* gate train */
308 	value = readl(reg_base + 0x50);
309 	if ((0 == (value & GENMASK(15, 0))) ||
310 	    (0 == (value & GENMASK(31, 16)))) {
311 		need_retrain = 1;
312 	}
313 #if 0
314 	if (((value >> 24) & 0xff) < 3)
315 		need_retrain = 1;
316 	else
317 		need_retrain = 0;
318 #endif
319 	debug("rO_DDRPHY_reg offset 0x50 = 0x%08x\n", value);
320 	debug("  gate training pass window\n");
321 	tmp = (((value & GENMASK(7, 0)) >> 0) * 100) / 255;
322 	debug("    module 0: %d.%03d\n", (value >> 8) & 0xff, tmp);
323         tmp = (((value & GENMASK(23, 16)) >> 0) * 100) / 255;
324 	debug("    module 1: %d.%03d\n", (value >> 24) & 0xff, tmp);
325 
326 	return need_retrain;
327 #else
328 	return 0;
329 #endif
330 }
331 
332 #define MC_TEST_PATTERN_N 8
333 static u32 as2600_sdrammc_test_pattern[MC_TEST_PATTERN_N] = {
334     0xcc33cc33, 0xff00ff00, 0xaa55aa55, 0x88778877,
335     0x92cc4d6e, 0x543d3cde, 0xf1e843c7, 0x7c61d253};
336 
337 #define TIMEOUT_DRAM	5000000
338 int ast2600_sdrammc_dg_test(struct dram_info *info, unsigned int datagen, u32 mode)
339 {
340 	unsigned int data;
341 	unsigned int timeout = 0;
342 	struct ast2600_sdrammc_regs *regs = info->regs;
343 
344 	writel(0, &regs->ecc_test_ctrl);
345 	if (mode == 0) {
346 		writel(0x00000085 | (datagen << 3), &regs->ecc_test_ctrl);
347 	} else {
348 		writel(0x000000C1 | (datagen << 3), &regs->ecc_test_ctrl);
349 	}
350 
351 	do {
352 		data = readl(&regs->ecc_test_ctrl) & GENMASK(13, 12);
353 
354 		if (data & BIT(13))
355 			return (0);
356 
357 		if (++timeout > TIMEOUT_DRAM) {
358 			printf("Timeout!!\n");
359 			writel(0, &regs->ecc_test_ctrl);
360 
361 			return (0);
362 		}
363 	} while (!data);
364 
365 	writel(0, &regs->ecc_test_ctrl);
366 
367 	return (1);
368 }
369 
370 int ast2600_sdrammc_cbr_test(struct dram_info *info)
371 {
372 	struct ast2600_sdrammc_regs *regs = info->regs;
373 	u32 i;
374 
375 	clrsetbits_le32(&regs->test_addr, GENMASK(30, 4), 0x7ffff0);
376 
377 	/* single */
378 	for (i=0; i<8; i++) {
379   		if(!ast2600_sdrammc_dg_test(info, i, 0))   return(0);
380 	}
381 
382 	/* burst */
383 	for (i=0; i<8; i++) {
384   		if(!ast2600_sdrammc_dg_test(info, i, i))   return(0);
385 	}
386 
387 	return(1);
388 }
389 
390 static int ast2600_sdrammc_test(struct dram_info *info)
391 {
392 	struct ast2600_sdrammc_regs *regs = info->regs;
393 
394 	u32 pass_cnt = 0;
395 	u32 fail_cnt = 0;
396 	u32 target_cnt = 2;
397 	u32 test_cnt = 0;
398 	u32 pattern;
399 	u32 i = 0;
400 	bool finish = false;
401 
402 	debug("sdram mc test:\n");
403 	while (finish == false) {
404 		pattern = as2600_sdrammc_test_pattern[i++];
405 		i = i % MC_TEST_PATTERN_N;
406 		debug("  pattern = %08X : ",pattern);
407 		writel(pattern, regs->test_init_val);
408 
409 		if (!ast2600_sdrammc_cbr_test(info)) {
410 			debug("fail\n");
411 			fail_cnt++;
412 		} else {
413 			debug("pass\n");
414 			pass_cnt++;
415 		}
416 
417 		if (++test_cnt == target_cnt) {
418 			finish = true;
419 		}
420 	}
421 	debug("statistics: pass/fail/total:%d/%d/%d\n", pass_cnt, fail_cnt,
422 	       target_cnt);
423 	return fail_cnt;
424 }
425 
426 /**
427  * scu500[14:13]
428  * 	2b'00: VGA memory size = 8MB
429  * 	2b'01: VGA memory size = 16MB
430  * 	2b'10: VGA memory size = 32MB
431  * 	2b'11: VGA memory size = 64MB
432  *
433  * mcr04[3:2]
434  * 	2b'00: VGA memory size = 8MB
435  * 	2b'01: VGA memory size = 16MB
436  * 	2b'10: VGA memory size = 32MB
437  * 	2b'11: VGA memory size = 64MB
438 */
439 static size_t ast2600_sdrammc_get_vga_mem_size(struct dram_info *info)
440 {
441         u32 vga_hwconf;
442         size_t vga_mem_size_base = 8 * 1024 * 1024;
443 
444 	vga_hwconf =
445 	    (readl(info->scu + AST_SCU_HW_STRAP) & SCU_HWSTRAP_VGAMEM_MASK) >>
446 	    SCU_HWSTRAP_VGAMEM_SHIFT;
447 
448 	clrsetbits_le32(&info->regs->config, SDRAM_CONF_VGA_SIZE_MASK,
449 			((vga_hwconf << SDRAM_CONF_VGA_SIZE_SHIFT) &
450 			 SDRAM_CONF_VGA_SIZE_MASK));
451 
452 	return vga_mem_size_base << vga_hwconf;
453 }
454 #if defined(CONFIG_FPGA_ASPEED) || defined(CONFIG_ASPEED_PALLADIUM)
455 static void ast2600_sdrammc_fpga_set_pll(struct dram_info *info)
456 {
457         u32 data;
458         u32 scu_base = (u32)info->scu;
459 
460         writel(0x00000303, scu_base + AST_SCU_FPGA_PLL);
461 
462         do {
463                 data = readl(scu_base + AST_SCU_FPGA_STATUS);
464         } while (!(data & 0x100));
465 
466         writel(0x00000103, scu_base + AST_SCU_FPGA_PLL);
467 }
468 
469 static int ast2600_sdrammc_search_read_window(struct dram_info *info)
470 {
471         u32 pll, pll_min, pll_max, dat1, offset;
472         u32 win = 0x03, gwin = 0, gwinsize = 0;
473         u32 phy_setting = (u32)info->phy_setting;
474 
475 #ifdef CONFIG_ASPEED_PALLADIUM
476 	writel(0xc, phy_setting + 0x0000);
477 	return (1);
478 #endif
479         writel(SEARCH_RDWIN_PTRN_0, SEARCH_RDWIN_ANCHOR_0);
480         writel(SEARCH_RDWIN_PTRN_1, SEARCH_RDWIN_ANCHOR_1);
481 
482         while (gwin == 0) {
483                 while (!(win & 0x80)) {
484                         debug("Window = 0x%X\n", win);
485                         writel(win, phy_setting + 0x0000);
486 
487                         dat1 = readl(SEARCH_RDWIN_ANCHOR_0);
488                         dat1 += readl(SEARCH_RDWIN_ANCHOR_1);
489                         while (dat1 == SEARCH_RDWIN_PTRN_SUM) {
490                                 ast2600_sdrammc_fpga_set_pll(info);
491                                 dat1 = readl(SEARCH_RDWIN_ANCHOR_0);
492                                 dat1 += readl(SEARCH_RDWIN_ANCHOR_1);
493                         }
494 
495                         pll_min = 0xfff;
496                         pll_max = 0x0;
497                         pll = 0;
498                         while (pll_max > 0 || pll < 256) {
499                                 ast2600_sdrammc_fpga_set_pll(info);
500                                 dat1 = readl(SEARCH_RDWIN_ANCHOR_0);
501                                 dat1 += readl(SEARCH_RDWIN_ANCHOR_1);
502                                 if (dat1 == SEARCH_RDWIN_PTRN_SUM) {
503                                         if (pll_min > pll) {
504                                                 pll_min = pll;
505                                         }
506                                         if (pll_max < pll) {
507                                                 pll_max = pll;
508                                         }
509                                         debug("%3d_(%3d:%3d)\n", pll, pll_min,
510                                                pll_max);
511                                 } else if (pll_max > 0) {
512                                         pll_min = pll_max - pll_min;
513                                         if (gwinsize < pll_min) {
514                                                 gwin = win;
515                                                 gwinsize = pll_min;
516                                         }
517                                         break;
518                                 }
519                                 pll += 1;
520                         }
521 
522                         if (gwin != 0 && pll_max == 0) {
523                                 break;
524                         }
525                         win = win << 1;
526                 }
527                 if (gwin == 0) {
528                         win = 0x7;
529                 }
530         }
531         debug("Set PLL Read Gating Window = %x\n", gwin);
532         writel(gwin, phy_setting + 0x0000);
533 
534         debug("PLL Read Window training\n");
535         pll_min = 0xfff;
536         pll_max = 0x0;
537 
538         debug("Search Window Start\n");
539         dat1 = readl(SEARCH_RDWIN_ANCHOR_0);
540         dat1 += readl(SEARCH_RDWIN_ANCHOR_1);
541         while (dat1 == SEARCH_RDWIN_PTRN_SUM) {
542                 ast2600_sdrammc_fpga_set_pll(info);
543                 dat1 = readl(SEARCH_RDWIN_ANCHOR_0);
544                 dat1 += readl(SEARCH_RDWIN_ANCHOR_1);
545         }
546 
547         debug("Search Window Margin\n");
548         pll = 0;
549         while (pll_max > 0 || pll < 256) {
550                 ast2600_sdrammc_fpga_set_pll(info);
551                 dat1 = readl(SEARCH_RDWIN_ANCHOR_0);
552                 dat1 += readl(SEARCH_RDWIN_ANCHOR_1);
553                 if (dat1 == SEARCH_RDWIN_PTRN_SUM) {
554                         if (pll_min > pll) {
555                                 pll_min = pll;
556                         }
557                         if (pll_max < pll) {
558                                 pll_max = pll;
559                         }
560                         debug("%3d_(%3d:%3d)\n", pll, pll_min, pll_max);
561                 } else if (pll_max > 0 && (pll_max - pll_min) > 20) {
562                         break;
563                 } else if (pll_max > 0) {
564                         pll_min = 0xfff;
565                         pll_max = 0x0;
566                 }
567                 pll += 1;
568         }
569         if (pll_min < pll_max) {
570                 debug("PLL Read window = %d\n", (pll_max - pll_min));
571                 offset = (pll_max - pll_min) >> 1;
572                 pll_min = 0xfff;
573                 pll = 0;
574                 while (pll < (pll_min + offset)) {
575                         ast2600_sdrammc_fpga_set_pll(info);
576                         dat1 = readl(SEARCH_RDWIN_ANCHOR_0);
577                         dat1 += readl(SEARCH_RDWIN_ANCHOR_1);
578                         if (dat1 == SEARCH_RDWIN_PTRN_SUM) {
579                                 if (pll_min > pll) {
580                                         pll_min = pll;
581                                 }
582                                 debug("%d\n", pll);
583                         } else {
584                                 pll_min = 0xfff;
585                                 pll_max = 0x0;
586                         }
587                         pll += 1;
588                 }
589                 return (1);
590         } else {
591                 debug("PLL Read window training fail\n");
592                 return (0);
593         }
594 }
595 #endif /* end of "#if defined(CONFIG_FPGA_ASPEED) ||                           \
596 	  defined(CONFIG_ASPEED_PALLADIUM)" */
597 
598 /*
599  * Find out RAM size and save it in dram_info
600  *
601  * The procedure is taken from Aspeed SDK
602  */
603 static void ast2600_sdrammc_calc_size(struct dram_info *info)
604 {
605 	/* The controller supports 256/512/1024/2048 MB ram */
606 	size_t ram_size = SDRAM_MIN_SIZE;
607 	const int write_test_offset = 0x100000;
608 	u32 test_pattern = 0xdeadbeef;
609 	u32 cap_param = SDRAM_CONF_CAP_2048M;
610 	u32 refresh_timing_param = DDR4_TRFC;
611 	const u32 write_addr_base = CONFIG_SYS_SDRAM_BASE + write_test_offset;
612 
613 	for (ram_size = SDRAM_MAX_SIZE; ram_size > SDRAM_MIN_SIZE;
614 	     ram_size >>= 1) {
615 		writel(test_pattern, write_addr_base + (ram_size >> 1));
616 		test_pattern = (test_pattern >> 4) | (test_pattern << 28);
617 	}
618 
619 	/* One last write to overwrite all wrapped values */
620 	writel(test_pattern, write_addr_base);
621 
622 	/* Reset the pattern and see which value was really written */
623 	test_pattern = 0xdeadbeef;
624 	for (ram_size = SDRAM_MAX_SIZE; ram_size > SDRAM_MIN_SIZE;
625 	     ram_size >>= 1) {
626 		if (readl(write_addr_base + (ram_size >> 1)) == test_pattern)
627 			break;
628 
629 		--cap_param;
630 		refresh_timing_param >>= 8;
631 		test_pattern = (test_pattern >> 4) | (test_pattern << 28);
632 	}
633 
634 	clrsetbits_le32(&info->regs->ac_timing[1],
635 			(SDRAM_AC_TRFC_MASK << SDRAM_AC_TRFC_SHIFT),
636 			((refresh_timing_param & SDRAM_AC_TRFC_MASK)
637 			 << SDRAM_AC_TRFC_SHIFT));
638 
639 	info->info.base = CONFIG_SYS_SDRAM_BASE;
640 	info->info.size = ram_size - ast2600_sdrammc_get_vga_mem_size(info);
641 	clrsetbits_le32(
642 	    &info->regs->config, SDRAM_CONF_CAP_MASK,
643 	    ((cap_param << SDRAM_CONF_CAP_SHIFT) & SDRAM_CONF_CAP_MASK));
644 }
645 
646 static int ast2600_sdrammc_init_ddr4(struct dram_info *info)
647 {
648         const u32 power_ctrl = MCR34_CKE_EN | MCR34_AUTOPWRDN_EN |
649                                MCR34_MREQ_BYPASS_DIS | MCR34_RESETN_DIS |
650                                MCR34_ODT_EN | MCR34_ODT_AUTO_ON |
651                                (0x1 << MCR34_ODT_EXT_SHIFT);
652 
653         /* init SDRAM-PHY only on real chip */
654 	ast2600_sdramphy_init(ast2600_sdramphy_config, info);
655         writel((MCR34_CKE_EN | MCR34_MREQI_DIS | MCR34_RESETN_DIS),
656                &info->regs->power_ctrl);
657 	udelay(5);
658 	ast2600_sdramphy_kick_training(info);
659 	udelay(500);
660         writel(SDRAM_RESET_DLL_ZQCL_EN, &info->regs->refresh_timing);
661 
662         writel(MCR30_SET_MR(3), &info->regs->mode_setting_control);
663         writel(MCR30_SET_MR(6), &info->regs->mode_setting_control);
664         writel(MCR30_SET_MR(5), &info->regs->mode_setting_control);
665         writel(MCR30_SET_MR(4), &info->regs->mode_setting_control);
666         writel(MCR30_SET_MR(2), &info->regs->mode_setting_control);
667         writel(MCR30_SET_MR(1), &info->regs->mode_setting_control);
668         writel(MCR30_SET_MR(0) | MCR30_RESET_DLL_DELAY_EN,
669                &info->regs->mode_setting_control);
670 
671 #if defined(CONFIG_FPGA_ASPEED) || defined(CONFIG_ASPEED_PALLADIUM)
672 
673         writel(SDRAM_REFRESH_EN | SDRAM_RESET_DLL_ZQCL_EN |
674                    (0x5d << SDRAM_REFRESH_PERIOD_SHIFT),
675                &info->regs->refresh_timing);
676 #else
677         writel(SDRAM_REFRESH_EN | SDRAM_RESET_DLL_ZQCL_EN |
678                    (0x5f << SDRAM_REFRESH_PERIOD_SHIFT),
679                &info->regs->refresh_timing);
680 #endif
681 
682         /* wait self-refresh idle */
683         while (readl(&info->regs->power_ctrl) & MCR34_SELF_REFRESH_STATUS_MASK)
684                 ;
685 
686 #if defined(CONFIG_FPGA_ASPEED) || defined(CONFIG_ASPEED_PALLADIUM)
687         writel(SDRAM_REFRESH_EN | SDRAM_LOW_PRI_REFRESH_EN |
688                    SDRAM_REFRESH_ZQCS_EN |
689                    (0x5d << SDRAM_REFRESH_PERIOD_SHIFT) |
690                    (0x4000 << SDRAM_REFRESH_PERIOD_ZQCS_SHIFT),
691                &info->regs->refresh_timing);
692 #else
693         writel(SDRAM_REFRESH_EN | SDRAM_LOW_PRI_REFRESH_EN |
694                    SDRAM_REFRESH_ZQCS_EN |
695                    (0x5f << SDRAM_REFRESH_PERIOD_SHIFT) |
696                    (0x42aa << SDRAM_REFRESH_PERIOD_ZQCS_SHIFT),
697                &info->regs->refresh_timing);
698 #endif
699 
700         writel(power_ctrl, &info->regs->power_ctrl);
701 	udelay(500);
702 
703 #if defined(CONFIG_FPGA_ASPEED)
704         /* toggle Vref training */
705         setbits_le32(&info->regs->mr6_mode_setting, 0x80);
706         writel(MCR30_RESET_DLL_DELAY_EN | MCR30_SET_MR(6),
707                &info->regs->mode_setting_control);
708         clrbits_le32(&info->regs->mr6_mode_setting, 0x80);
709         writel(MCR30_RESET_DLL_DELAY_EN | MCR30_SET_MR(6),
710                &info->regs->mode_setting_control);
711 #endif
712 	return 0;
713 }
714 
715 static void ast2600_sdrammc_unlock(struct dram_info *info)
716 {
717 	writel(SDRAM_UNLOCK_KEY, &info->regs->protection_key);
718 	while (!readl(&info->regs->protection_key))
719 		;
720 }
721 
722 static void ast2600_sdrammc_lock(struct dram_info *info)
723 {
724 	writel(~SDRAM_UNLOCK_KEY, &info->regs->protection_key);
725 	while (readl(&info->regs->protection_key))
726 		;
727 }
728 
729 static void ast2600_sdrammc_common_init(struct ast2600_sdrammc_regs *regs)
730 {
731 	int i;
732 
733         writel(MCR34_MREQI_DIS | MCR34_RESETN_DIS, &regs->power_ctrl);
734         writel(SDRAM_VIDEO_UNLOCK_KEY, &regs->gm_protection_key);
735         writel(0x10 << MCR38_RW_MAX_GRANT_CNT_RQ_SHIFT,
736                &regs->arbitration_ctrl);
737         writel(0xFFBBFFF4, &regs->req_limit_mask);
738 
739 	for (i = 0; i < ARRAY_SIZE(ddr_max_grant_params); ++i)
740                 writel(ddr_max_grant_params[i], &regs->max_grant_len[i]);
741 
742         writel(MCR50_RESET_ALL_INTR, &regs->intr_ctrl);
743 
744         /* FIXME: the sample code does NOT match the datasheet */
745         writel(0x07FFFFFF, &regs->ecc_range_ctrl);
746 
747         writel(0, &regs->ecc_test_ctrl);
748         writel(0, &regs->test_addr);
749         writel(0, &regs->test_fail_dq_bit);
750         writel(0, &regs->test_init_val);
751 
752         writel(0xFFFFFFFF, &regs->req_input_ctrl);
753         writel(0, &regs->req_high_pri_ctrl);
754 
755         udelay(600);
756 
757 #ifdef CONFIG_ASPEED_DDR4_DUALX8
758 	writel(0x37, &regs->config);
759 #else
760 	writel(0x17, &regs->config);
761 #endif
762 
763 	/* load controller setting */
764 	for (i = 0; i < ARRAY_SIZE(ddr4_ac_timing); ++i)
765 		writel(ddr4_ac_timing[i], &regs->ac_timing[i]);
766 
767 	writel(DDR4_MR01_MODE, &regs->mr01_mode_setting);
768 	writel(DDR4_MR23_MODE, &regs->mr23_mode_setting);
769 	writel(DDR4_MR45_MODE, &regs->mr45_mode_setting);
770 	writel(DDR4_MR6_MODE, &regs->mr6_mode_setting);
771 }
772 
773 #ifdef CONFIG_ASPEED_ECC
774 static void ast2600_sdrammc_ecc_enable(struct dram_info *info)
775 {
776 	struct ast2600_sdrammc_regs *regs = info->regs;
777 	u32 reg;
778 
779 	writel(((info->info.size >> 20) - 1) << 20, &regs->ecc_range_ctrl);
780 	reg = readl(&regs->config) |
781 	      (SDRAM_CONF_ECC_EN | SDRAM_CONF_ECC_AUTO_SCRUBBING);
782 	writel(reg, &regs->config);
783 
784 	writel(0, &regs->test_init_val);
785 	writel(0, &regs->test_addr);
786 	writel(0x221, &regs->ecc_test_ctrl);
787 	while (0 == (readl(&regs->ecc_test_ctrl) & BIT(12)))
788 		;
789 	writel(0, &regs->ecc_test_ctrl);
790 	writel(BIT(31), &regs->intr_ctrl);
791 	writel(0, &regs->intr_ctrl);
792 
793 	/* reported size is updated */
794 	info->info.size -= (CONFIG_ASPEED_VIDEO_SIZE + CONFIG_ASPEED_CRT_SIZE) *
795 			   SDRAM_SIZE_1MB;
796 	info->info.size = (info->info.size / 9) * 8;
797 	printf("ECC enable, ");
798 }
799 #endif
800 
801 static int ast2600_sdrammc_probe(struct udevice *dev)
802 {
803 	struct dram_info *priv = (struct dram_info *)dev_get_priv(dev);
804 	struct ast2600_sdrammc_regs *regs = priv->regs;
805 	struct udevice *clk_dev;
806 	int ret;
807 	volatile uint32_t reg;
808 
809 	/* find SCU base address from clock device */
810 	ret = uclass_get_device_by_driver(UCLASS_CLK, DM_GET_DRIVER(aspeed_scu),
811                                           &clk_dev);
812 	if (ret) {
813 		debug("clock device not defined\n");
814 		return ret;
815 	}
816 
817 	priv->scu = devfdt_get_addr_ptr(clk_dev);
818 	if (IS_ERR(priv->scu)) {
819 		debug("%s(): can't get SCU\n", __func__);
820 		return PTR_ERR(priv->scu);
821 	}
822 
823 	if (readl(priv->scu + AST_SCU_HANDSHAKE) & SCU_SDRAM_INIT_READY_MASK) {
824 		printf("already initialized, ");
825 		ast2600_sdrammc_calc_size(priv);
826 #ifdef CONFIG_ASPEED_ECC
827 		ast2600_sdrammc_ecc_enable(priv);
828 #endif
829 		return 0;
830 	}
831 
832 #ifdef AST2600_SDRAMMC_MANUAL_CLK
833 	reg = readl(priv->scu + AST_SCU_MPLL);
834 	reg &= ~(BIT(24) | GENMASK(22, 0));
835 	reg |= (BIT(25) | BIT(23) | SCU_MPLL_FREQ_CFG);
836 	writel(reg, priv->scu + AST_SCU_MPLL);
837         writel(SCU_MPLL_EXT_CFG, priv->scu + AST_SCU_MPLL_EXT);
838 	udelay(100);
839 	reg &= ~(BIT(25) | BIT(23));
840 	writel(reg, priv->scu + AST_SCU_MPLL);
841 	while(0 == (readl(priv->scu + AST_SCU_MPLL_EXT) & BIT(31)));
842 #else
843 	ret = clk_get_by_index(dev, 0, &priv->ddr_clk);
844 	if (ret) {
845 		debug("DDR:No CLK\n");
846 		return ret;
847 	}
848 	clk_set_rate(&priv->ddr_clk, priv->clock_rate);
849 #endif
850 
851 #if 0
852 	/* FIXME: enable the following code if reset-driver is ready */
853 	struct reset_ctl reset_ctl;
854 	ret = reset_get_by_index(dev, 0, &reset_ctl);
855 	if (ret) {
856 		debug("%s(): Failed to get reset signal\n", __func__);
857 		return ret;
858 	}
859 
860 	ret = reset_assert(&reset_ctl);
861 	if (ret) {
862 		debug("%s(): SDRAM reset failed: %u\n", __func__, ret);
863 		return ret;
864 	}
865 #endif
866 
867 	ast2600_sdrammc_unlock(priv);
868 	ast2600_sdrammc_common_init(regs);
869 L_ast2600_sdramphy_train:
870 	ast2600_sdrammc_init_ddr4(priv);
871 
872 #if defined(CONFIG_FPGA_ASPEED) || defined(CONFIG_ASPEED_PALLADIUM)
873         ast2600_sdrammc_search_read_window(priv);
874 #else
875 	/* make sure DDR-PHY is ready before access */
876 	do {
877 		reg = readl(priv->phy_status) & BIT(1);
878 	} while(reg == 0);
879 #endif
880 
881 	if (0 != ast2600_sdramphy_check_status(priv)) {
882 		printf("DDR4 PHY training fail, retrain\n");
883 		goto L_ast2600_sdramphy_train;
884 	}
885 
886 	ast2600_sdrammc_calc_size(priv);
887 
888         if (0 != ast2600_sdrammc_test(priv)) {
889 		printf("%s: DDR4 init fail\n", __func__);
890 		return -EINVAL;
891 	}
892 
893 #ifdef CONFIG_ASPEED_ECC
894 	ast2600_sdrammc_ecc_enable(priv);
895 #endif
896 
897 	writel(readl(priv->scu + AST_SCU_HANDSHAKE) | SCU_SDRAM_INIT_READY_MASK,
898 	       priv->scu + AST_SCU_HANDSHAKE);
899 
900 	clrbits_le32(&regs->intr_ctrl, MCR50_RESET_ALL_INTR);
901 	ast2600_sdrammc_lock(priv);
902 	return 0;
903 }
904 
905 static int ast2600_sdrammc_ofdata_to_platdata(struct udevice *dev)
906 {
907 	struct dram_info *priv = dev_get_priv(dev);
908 
909 	priv->regs = (void *)(uintptr_t)devfdt_get_addr_index(dev, 0);
910 	priv->phy_setting = (void *)(uintptr_t)devfdt_get_addr_index(dev, 1);
911 	priv->phy_status = (void *)(uintptr_t)devfdt_get_addr_index(dev, 2);
912 
913 	priv->clock_rate = fdtdec_get_int(gd->fdt_blob, dev_of_offset(dev),
914 					  "clock-frequency", 0);
915 	if (!priv->clock_rate) {
916 		debug("DDR Clock Rate not defined\n");
917 		return -EINVAL;
918 	}
919 
920 	return 0;
921 }
922 
923 static int ast2600_sdrammc_get_info(struct udevice *dev, struct ram_info *info)
924 {
925 	struct dram_info *priv = dev_get_priv(dev);
926 
927 	*info = priv->info;
928 
929 	return 0;
930 }
931 
932 static struct ram_ops ast2600_sdrammc_ops = {
933 	.get_info = ast2600_sdrammc_get_info,
934 };
935 
936 static const struct udevice_id ast2600_sdrammc_ids[] = {
937 	{ .compatible = "aspeed,ast2600-sdrammc" },
938 	{ }
939 };
940 
941 U_BOOT_DRIVER(sdrammc_ast2600) = {
942 	.name = "aspeed_ast2600_sdrammc",
943 	.id = UCLASS_RAM,
944 	.of_match = ast2600_sdrammc_ids,
945 	.ops = &ast2600_sdrammc_ops,
946 	.ofdata_to_platdata = ast2600_sdrammc_ofdata_to_platdata,
947 	.probe = ast2600_sdrammc_probe,
948 	.priv_auto_alloc_size = sizeof(struct dram_info),
949 };
950