]>
Commit | Line | Data |
---|---|---|
2a6c2d7a | 1 | /* |
744713a6 | 2 | * Copyright 2008-2012 Freescale Semiconductor, Inc. |
2a6c2d7a | 3 | * |
5b8031cc | 4 | * SPDX-License-Identifier: GPL-2.0 |
2a6c2d7a KG |
5 | */ |
6 | ||
7 | #include <common.h> | |
8 | #include <asm/io.h> | |
5614e71b | 9 | #include <fsl_ddr_sdram.h> |
d2a9568c | 10 | #include <asm/processor.h> |
2a6c2d7a KG |
11 | |
12 | #if (CONFIG_CHIP_SELECTS_PER_CTRL > 4) | |
13 | #error Invalid setting for CONFIG_CHIP_SELECTS_PER_CTRL | |
14 | #endif | |
15 | ||
c63e1370 YS |
16 | /* |
17 | * regs has the to-be-set values for DDR controller registers | |
18 | * ctrl_num is the DDR controller number | |
19 | * step: 0 goes through the initialization in one pass | |
20 | * 1 sets registers and returns before enabling controller | |
21 | * 2 resumes from step 1 and continues to initialize | |
22 | * Dividing the initialization to two steps to deassert DDR reset signal | |
23 | * to comply with JEDEC specs for RDIMMs. | |
24 | */ | |
2a6c2d7a | 25 | void fsl_ddr_set_memctl_regs(const fsl_ddr_cfg_regs_t *regs, |
c63e1370 | 26 | unsigned int ctrl_num, int step) |
2a6c2d7a | 27 | { |
f31cfd19 | 28 | unsigned int i, bus_width; |
9a17eb5b | 29 | struct ccsr_ddr __iomem *ddr; |
e1be0d25 | 30 | u32 temp_sdram_cfg; |
f31cfd19 | 31 | u32 total_gb_size_per_controller; |
23028d69 | 32 | int timeout; |
91671913 | 33 | #ifdef CONFIG_SYS_FSL_ERRATUM_DDR111_DDR134 |
23028d69 | 34 | int timeout_save; |
91671913 | 35 | volatile ccsr_local_ecm_t *ecm = (void *)CONFIG_SYS_MPC85xx_ECM_ADDR; |
eb672e92 YS |
36 | unsigned int csn_bnds_backup = 0, cs_sa, cs_ea, *csn_bnds_t; |
37 | int csn = -1; | |
91671913 | 38 | #endif |
76356eb5 YS |
39 | #ifdef CONFIG_SYS_FSL_ERRATUM_DDR_A003 |
40 | u32 save1, save2; | |
41 | #endif | |
2a6c2d7a KG |
42 | |
43 | switch (ctrl_num) { | |
44 | case 0: | |
5614e71b | 45 | ddr = (void *)CONFIG_SYS_FSL_DDR_ADDR; |
2a6c2d7a | 46 | break; |
5614e71b | 47 | #if defined(CONFIG_SYS_FSL_DDR2_ADDR) && (CONFIG_NUM_DDR_CONTROLLERS > 1) |
2a6c2d7a | 48 | case 1: |
5614e71b | 49 | ddr = (void *)CONFIG_SYS_FSL_DDR2_ADDR; |
2a6c2d7a | 50 | break; |
a4c66509 | 51 | #endif |
5614e71b | 52 | #if defined(CONFIG_SYS_FSL_DDR3_ADDR) && (CONFIG_NUM_DDR_CONTROLLERS > 2) |
a4c66509 | 53 | case 2: |
5614e71b | 54 | ddr = (void *)CONFIG_SYS_FSL_DDR3_ADDR; |
a4c66509 YS |
55 | break; |
56 | #endif | |
5614e71b | 57 | #if defined(CONFIG_SYS_FSL_DDR4_ADDR) && (CONFIG_NUM_DDR_CONTROLLERS > 3) |
a4c66509 | 58 | case 3: |
5614e71b | 59 | ddr = (void *)CONFIG_SYS_FSL_DDR4_ADDR; |
a4c66509 YS |
60 | break; |
61 | #endif | |
2a6c2d7a KG |
62 | default: |
63 | printf("%s unexpected ctrl_num = %u\n", __FUNCTION__, ctrl_num); | |
64 | return; | |
65 | } | |
66 | ||
c63e1370 YS |
67 | if (step == 2) |
68 | goto step2; | |
69 | ||
f31cfd19 YS |
70 | if (regs->ddr_eor) |
71 | out_be32(&ddr->eor, regs->ddr_eor); | |
eb672e92 | 72 | #ifdef CONFIG_SYS_FSL_ERRATUM_DDR111_DDR134 |
744713a6 | 73 | debug("Workaround for ERRATUM_DDR111_DDR134\n"); |
eb672e92 YS |
74 | for (i = 0; i < CONFIG_CHIP_SELECTS_PER_CTRL; i++) { |
75 | cs_sa = (regs->cs[i].bnds >> 16) & 0xfff; | |
76 | cs_ea = regs->cs[i].bnds & 0xfff; | |
77 | if ((cs_sa <= 0xff) && (cs_ea >= 0xff)) { | |
78 | csn = i; | |
79 | csn_bnds_backup = regs->cs[i].bnds; | |
80 | csn_bnds_t = (unsigned int *) ®s->cs[i].bnds; | |
535a159a YS |
81 | if (cs_ea > 0xeff) |
82 | *csn_bnds_t = regs->cs[i].bnds + 0x01000000; | |
83 | else | |
84 | *csn_bnds_t = regs->cs[i].bnds + 0x01000100; | |
eb672e92 YS |
85 | debug("Found cs%d_bns (0x%08x) covering 0xff000000, " |
86 | "change it to 0x%x\n", | |
87 | csn, csn_bnds_backup, regs->cs[i].bnds); | |
88 | break; | |
89 | } | |
90 | } | |
91 | #endif | |
2a6c2d7a KG |
92 | for (i = 0; i < CONFIG_CHIP_SELECTS_PER_CTRL; i++) { |
93 | if (i == 0) { | |
94 | out_be32(&ddr->cs0_bnds, regs->cs[i].bnds); | |
95 | out_be32(&ddr->cs0_config, regs->cs[i].config); | |
96 | out_be32(&ddr->cs0_config_2, regs->cs[i].config_2); | |
97 | ||
98 | } else if (i == 1) { | |
99 | out_be32(&ddr->cs1_bnds, regs->cs[i].bnds); | |
100 | out_be32(&ddr->cs1_config, regs->cs[i].config); | |
101 | out_be32(&ddr->cs1_config_2, regs->cs[i].config_2); | |
102 | ||
103 | } else if (i == 2) { | |
104 | out_be32(&ddr->cs2_bnds, regs->cs[i].bnds); | |
105 | out_be32(&ddr->cs2_config, regs->cs[i].config); | |
106 | out_be32(&ddr->cs2_config_2, regs->cs[i].config_2); | |
107 | ||
108 | } else if (i == 3) { | |
109 | out_be32(&ddr->cs3_bnds, regs->cs[i].bnds); | |
110 | out_be32(&ddr->cs3_config, regs->cs[i].config); | |
111 | out_be32(&ddr->cs3_config_2, regs->cs[i].config_2); | |
112 | } | |
113 | } | |
114 | ||
115 | out_be32(&ddr->timing_cfg_3, regs->timing_cfg_3); | |
116 | out_be32(&ddr->timing_cfg_0, regs->timing_cfg_0); | |
117 | out_be32(&ddr->timing_cfg_1, regs->timing_cfg_1); | |
118 | out_be32(&ddr->timing_cfg_2, regs->timing_cfg_2); | |
2a6c2d7a KG |
119 | out_be32(&ddr->sdram_mode, regs->ddr_sdram_mode); |
120 | out_be32(&ddr->sdram_mode_2, regs->ddr_sdram_mode_2); | |
e1fd16b6 YS |
121 | out_be32(&ddr->sdram_mode_3, regs->ddr_sdram_mode_3); |
122 | out_be32(&ddr->sdram_mode_4, regs->ddr_sdram_mode_4); | |
123 | out_be32(&ddr->sdram_mode_5, regs->ddr_sdram_mode_5); | |
124 | out_be32(&ddr->sdram_mode_6, regs->ddr_sdram_mode_6); | |
125 | out_be32(&ddr->sdram_mode_7, regs->ddr_sdram_mode_7); | |
126 | out_be32(&ddr->sdram_mode_8, regs->ddr_sdram_mode_8); | |
2a6c2d7a KG |
127 | out_be32(&ddr->sdram_md_cntl, regs->ddr_sdram_md_cntl); |
128 | out_be32(&ddr->sdram_interval, regs->ddr_sdram_interval); | |
129 | out_be32(&ddr->sdram_data_init, regs->ddr_data_init); | |
130 | out_be32(&ddr->sdram_clk_cntl, regs->ddr_sdram_clk_cntl); | |
2a6c2d7a KG |
131 | out_be32(&ddr->timing_cfg_4, regs->timing_cfg_4); |
132 | out_be32(&ddr->timing_cfg_5, regs->timing_cfg_5); | |
133 | out_be32(&ddr->ddr_zq_cntl, regs->ddr_zq_cntl); | |
134 | out_be32(&ddr->ddr_wrlvl_cntl, regs->ddr_wrlvl_cntl); | |
cb93071b YS |
135 | #ifndef CONFIG_SYS_FSL_DDR_EMU |
136 | /* | |
137 | * Skip these two registers if running on emulator | |
138 | * because emulator doesn't have skew between bytes. | |
139 | */ | |
140 | ||
57495e4e YS |
141 | if (regs->ddr_wrlvl_cntl_2) |
142 | out_be32(&ddr->ddr_wrlvl_cntl_2, regs->ddr_wrlvl_cntl_2); | |
143 | if (regs->ddr_wrlvl_cntl_3) | |
144 | out_be32(&ddr->ddr_wrlvl_cntl_3, regs->ddr_wrlvl_cntl_3); | |
cb93071b | 145 | #endif |
57495e4e | 146 | |
2a6c2d7a KG |
147 | out_be32(&ddr->ddr_sr_cntr, regs->ddr_sr_cntr); |
148 | out_be32(&ddr->ddr_sdram_rcw_1, regs->ddr_sdram_rcw_1); | |
149 | out_be32(&ddr->ddr_sdram_rcw_2, regs->ddr_sdram_rcw_2); | |
d2a9568c | 150 | out_be32(&ddr->ddr_cdr1, regs->ddr_cdr1); |
a7787b78 TY |
151 | #ifdef CONFIG_DEEP_SLEEP |
152 | if (is_warm_boot()) { | |
153 | out_be32(&ddr->sdram_cfg_2, | |
154 | regs->ddr_sdram_cfg_2 & ~SDRAM_CFG2_D_INIT); | |
155 | out_be32(&ddr->init_addr, CONFIG_SYS_SDRAM_BASE); | |
156 | out_be32(&ddr->init_ext_addr, DDR_INIT_ADDR_EXT_UIA); | |
157 | ||
158 | /* DRAM VRef will not be trained */ | |
159 | out_be32(&ddr->ddr_cdr2, | |
160 | regs->ddr_cdr2 & ~DDR_CDR2_VREF_TRAIN_EN); | |
161 | } else | |
162 | #endif | |
163 | { | |
164 | out_be32(&ddr->sdram_cfg_2, regs->ddr_sdram_cfg_2); | |
165 | out_be32(&ddr->init_addr, regs->ddr_init_addr); | |
166 | out_be32(&ddr->init_ext_addr, regs->ddr_init_ext_addr); | |
167 | out_be32(&ddr->ddr_cdr2, regs->ddr_cdr2); | |
168 | } | |
d2a9568c YS |
169 | out_be32(&ddr->err_disable, regs->err_disable); |
170 | out_be32(&ddr->err_int_en, regs->err_int_en); | |
744713a6 YS |
171 | for (i = 0; i < 32; i++) { |
172 | if (regs->debug[i]) { | |
173 | debug("Write to debug_%d as %08x\n", i+1, regs->debug[i]); | |
174 | out_be32(&ddr->debug[i], regs->debug[i]); | |
175 | } | |
176 | } | |
a1d558a2 | 177 | #ifdef CONFIG_SYS_FSL_ERRATUM_A_004934 |
8444b536 | 178 | out_be32(&ddr->debug[28], 0x30003000); |
a1d558a2 | 179 | #endif |
2a6c2d7a | 180 | |
4108508a YS |
181 | #ifdef CONFIG_SYS_FSL_ERRATUM_DDR_A003474 |
182 | out_be32(&ddr->debug[12], 0x00000015); | |
183 | out_be32(&ddr->debug[21], 0x24000000); | |
184 | #endif /* CONFIG_SYS_FSL_ERRATUM_DDR_A003474 */ | |
185 | ||
c63e1370 YS |
186 | /* |
187 | * For RDIMMs, JEDEC spec requires clocks to be stable before reset is | |
188 | * deasserted. Clocks start when any chip select is enabled and clock | |
189 | * control register is set. Because all DDR components are connected to | |
190 | * one reset signal, this needs to be done in two steps. Step 1 is to | |
191 | * get the clocks started. Step 2 resumes after reset signal is | |
192 | * deasserted. | |
193 | */ | |
194 | if (step == 1) { | |
195 | udelay(200); | |
196 | return; | |
197 | } | |
198 | ||
199 | step2: | |
0ee84b88 ES |
200 | /* Set, but do not enable the memory */ |
201 | temp_sdram_cfg = regs->ddr_sdram_cfg; | |
e1be0d25 P |
202 | temp_sdram_cfg &= ~(SDRAM_CFG_MEM_EN); |
203 | out_be32(&ddr->sdram_cfg, temp_sdram_cfg); | |
fa8d23c0 | 204 | #ifdef CONFIG_SYS_FSL_ERRATUM_DDR_A003 |
744713a6 | 205 | debug("Workaround for ERRATUM_DDR_A003\n"); |
fa8d23c0 YS |
206 | if (regs->ddr_sdram_rcw_2 & 0x00f00000) { |
207 | out_be32(&ddr->timing_cfg_2, regs->timing_cfg_2 & 0xf07fffff); | |
208 | out_be32(&ddr->debug[2], 0x00000400); | |
209 | out_be32(&ddr->ddr_zq_cntl, regs->ddr_zq_cntl & 0x7fffffff); | |
210 | out_be32(&ddr->ddr_wrlvl_cntl, regs->ddr_wrlvl_cntl & 0x7fffffff); | |
211 | out_be32(&ddr->sdram_cfg_2, regs->ddr_sdram_cfg_2 & 0xffffffeb); | |
212 | out_be32(&ddr->mtcr, 0); | |
76356eb5 YS |
213 | save1 = in_be32(&ddr->debug[12]); |
214 | save2 = in_be32(&ddr->debug[21]); | |
fa8d23c0 YS |
215 | out_be32(&ddr->debug[12], 0x00000015); |
216 | out_be32(&ddr->debug[21], 0x24000000); | |
217 | out_be32(&ddr->sdram_interval, regs->ddr_sdram_interval & 0xffff); | |
218 | out_be32(&ddr->sdram_cfg, temp_sdram_cfg | SDRAM_CFG_BI | SDRAM_CFG_MEM_EN); | |
219 | ||
220 | asm volatile("sync;isync"); | |
221 | while (!(in_be32(&ddr->debug[1]) & 0x2)) | |
222 | ; | |
223 | ||
224 | switch (regs->ddr_sdram_rcw_2 & 0x00f00000) { | |
225 | case 0x00000000: | |
226 | out_be32(&ddr->sdram_md_cntl, | |
227 | MD_CNTL_MD_EN | | |
228 | MD_CNTL_CS_SEL_CS0_CS1 | | |
229 | 0x04000000 | | |
230 | MD_CNTL_WRCW | | |
231 | MD_CNTL_MD_VALUE(0x02)); | |
76356eb5 YS |
232 | #if (CONFIG_DIMM_SLOTS_PER_CTLR == 2) |
233 | if (!(regs->cs[2].config & SDRAM_CS_CONFIG_EN)) | |
234 | break; | |
235 | while (in_be32(&ddr->sdram_md_cntl) & MD_CNTL_MD_EN) | |
236 | ; | |
237 | out_be32(&ddr->sdram_md_cntl, | |
238 | MD_CNTL_MD_EN | | |
239 | MD_CNTL_CS_SEL_CS2_CS3 | | |
240 | 0x04000000 | | |
241 | MD_CNTL_WRCW | | |
242 | MD_CNTL_MD_VALUE(0x02)); | |
243 | #endif | |
fa8d23c0 YS |
244 | break; |
245 | case 0x00100000: | |
246 | out_be32(&ddr->sdram_md_cntl, | |
247 | MD_CNTL_MD_EN | | |
248 | MD_CNTL_CS_SEL_CS0_CS1 | | |
249 | 0x04000000 | | |
250 | MD_CNTL_WRCW | | |
251 | MD_CNTL_MD_VALUE(0x0a)); | |
76356eb5 YS |
252 | #if (CONFIG_DIMM_SLOTS_PER_CTLR == 2) |
253 | if (!(regs->cs[2].config & SDRAM_CS_CONFIG_EN)) | |
254 | break; | |
255 | while (in_be32(&ddr->sdram_md_cntl) & MD_CNTL_MD_EN) | |
256 | ; | |
257 | out_be32(&ddr->sdram_md_cntl, | |
258 | MD_CNTL_MD_EN | | |
259 | MD_CNTL_CS_SEL_CS2_CS3 | | |
260 | 0x04000000 | | |
261 | MD_CNTL_WRCW | | |
262 | MD_CNTL_MD_VALUE(0x0a)); | |
263 | #endif | |
fa8d23c0 YS |
264 | break; |
265 | case 0x00200000: | |
266 | out_be32(&ddr->sdram_md_cntl, | |
267 | MD_CNTL_MD_EN | | |
268 | MD_CNTL_CS_SEL_CS0_CS1 | | |
269 | 0x04000000 | | |
270 | MD_CNTL_WRCW | | |
271 | MD_CNTL_MD_VALUE(0x12)); | |
76356eb5 YS |
272 | #if (CONFIG_DIMM_SLOTS_PER_CTLR == 2) |
273 | if (!(regs->cs[2].config & SDRAM_CS_CONFIG_EN)) | |
274 | break; | |
275 | while (in_be32(&ddr->sdram_md_cntl) & MD_CNTL_MD_EN) | |
276 | ; | |
277 | out_be32(&ddr->sdram_md_cntl, | |
278 | MD_CNTL_MD_EN | | |
279 | MD_CNTL_CS_SEL_CS2_CS3 | | |
280 | 0x04000000 | | |
281 | MD_CNTL_WRCW | | |
282 | MD_CNTL_MD_VALUE(0x12)); | |
283 | #endif | |
fa8d23c0 YS |
284 | break; |
285 | case 0x00300000: | |
286 | out_be32(&ddr->sdram_md_cntl, | |
287 | MD_CNTL_MD_EN | | |
288 | MD_CNTL_CS_SEL_CS0_CS1 | | |
289 | 0x04000000 | | |
290 | MD_CNTL_WRCW | | |
291 | MD_CNTL_MD_VALUE(0x1a)); | |
76356eb5 YS |
292 | #if (CONFIG_DIMM_SLOTS_PER_CTLR == 2) |
293 | if (!(regs->cs[2].config & SDRAM_CS_CONFIG_EN)) | |
294 | break; | |
295 | while (in_be32(&ddr->sdram_md_cntl) & MD_CNTL_MD_EN) | |
296 | ; | |
297 | out_be32(&ddr->sdram_md_cntl, | |
298 | MD_CNTL_MD_EN | | |
299 | MD_CNTL_CS_SEL_CS2_CS3 | | |
300 | 0x04000000 | | |
301 | MD_CNTL_WRCW | | |
302 | MD_CNTL_MD_VALUE(0x1a)); | |
303 | #endif | |
fa8d23c0 YS |
304 | break; |
305 | default: | |
306 | out_be32(&ddr->sdram_md_cntl, | |
307 | MD_CNTL_MD_EN | | |
308 | MD_CNTL_CS_SEL_CS0_CS1 | | |
309 | 0x04000000 | | |
310 | MD_CNTL_WRCW | | |
311 | MD_CNTL_MD_VALUE(0x02)); | |
76356eb5 YS |
312 | #if (CONFIG_DIMM_SLOTS_PER_CTLR == 2) |
313 | if (!(regs->cs[2].config & SDRAM_CS_CONFIG_EN)) | |
314 | break; | |
315 | while (in_be32(&ddr->sdram_md_cntl) & MD_CNTL_MD_EN) | |
316 | ; | |
317 | out_be32(&ddr->sdram_md_cntl, | |
318 | MD_CNTL_MD_EN | | |
319 | MD_CNTL_CS_SEL_CS2_CS3 | | |
320 | 0x04000000 | | |
321 | MD_CNTL_WRCW | | |
322 | MD_CNTL_MD_VALUE(0x02)); | |
323 | #endif | |
fa8d23c0 YS |
324 | printf("Unsupported RC10\n"); |
325 | break; | |
326 | } | |
327 | ||
328 | while (in_be32(&ddr->sdram_md_cntl) & 0x80000000) | |
329 | ; | |
330 | udelay(6); | |
331 | out_be32(&ddr->sdram_cfg, temp_sdram_cfg); | |
332 | out_be32(&ddr->timing_cfg_2, regs->timing_cfg_2); | |
333 | out_be32(&ddr->debug[2], 0x0); | |
334 | out_be32(&ddr->ddr_zq_cntl, regs->ddr_zq_cntl); | |
335 | out_be32(&ddr->ddr_wrlvl_cntl, regs->ddr_wrlvl_cntl); | |
336 | out_be32(&ddr->sdram_cfg_2, regs->ddr_sdram_cfg_2); | |
76356eb5 YS |
337 | out_be32(&ddr->debug[12], save1); |
338 | out_be32(&ddr->debug[21], save2); | |
fa8d23c0 YS |
339 | out_be32(&ddr->sdram_interval, regs->ddr_sdram_interval); |
340 | ||
341 | } | |
342 | #endif | |
2a6c2d7a | 343 | /* |
ae5f943b DL |
344 | * For 8572 DDR1 erratum - DDR controller may enter illegal state |
345 | * when operatiing in 32-bit bus mode with 4-beat bursts, | |
346 | * This erratum does not affect DDR3 mode, only for DDR2 mode. | |
2a6c2d7a | 347 | */ |
eb0aff77 | 348 | #ifdef CONFIG_SYS_FSL_ERRATUM_DDR_115 |
744713a6 | 349 | debug("Workaround for ERRATUM_DDR_115\n"); |
2a6c2d7a | 350 | if ((((in_be32(&ddr->sdram_cfg) >> 24) & 0x7) == SDRAM_TYPE_DDR2) |
ae5f943b | 351 | && in_be32(&ddr->sdram_cfg) & 0x80000) { |
2a6c2d7a | 352 | /* set DEBUG_1[31] */ |
d2a9568c | 353 | setbits_be32(&ddr->debug[0], 1); |
2a6c2d7a | 354 | } |
ae5f943b | 355 | #endif |
91671913 | 356 | #ifdef CONFIG_SYS_FSL_ERRATUM_DDR111_DDR134 |
744713a6 | 357 | debug("Workaround for ERRATUM_DDR111_DDR134\n"); |
91671913 YS |
358 | /* |
359 | * This is the combined workaround for DDR111 and DDR134 | |
360 | * following the published errata for MPC8572 | |
361 | */ | |
362 | ||
363 | /* 1. Set EEBACR[3] */ | |
364 | setbits_be32(&ecm->eebacr, 0x10000000); | |
365 | debug("Setting EEBACR[3] to 0x%08x\n", in_be32(&ecm->eebacr)); | |
366 | ||
367 | /* 2. Set DINIT in SDRAM_CFG_2*/ | |
368 | setbits_be32(&ddr->sdram_cfg_2, SDRAM_CFG2_D_INIT); | |
369 | debug("Setting sdram_cfg_2[D_INIT] to 0x%08x\n", | |
370 | in_be32(&ddr->sdram_cfg_2)); | |
371 | ||
372 | /* 3. Set DEBUG_3[21] */ | |
373 | setbits_be32(&ddr->debug[2], 0x400); | |
374 | debug("Setting DEBUG_3[21] to 0x%08x\n", in_be32(&ddr->debug[2])); | |
375 | ||
376 | #endif /* part 1 of the workaound */ | |
2a6c2d7a KG |
377 | |
378 | /* | |
c360ceac | 379 | * 500 painful micro-seconds must elapse between |
2a6c2d7a | 380 | * the DDR clock setup and the DDR config enable. |
c360ceac DL |
381 | * DDR2 need 200 us, and DDR3 need 500 us from spec, |
382 | * we choose the max, that is 500 us for all of case. | |
2a6c2d7a | 383 | */ |
c360ceac | 384 | udelay(500); |
2a6c2d7a KG |
385 | asm volatile("sync;isync"); |
386 | ||
aade2004 | 387 | #ifdef CONFIG_DEEP_SLEEP |
a7787b78 | 388 | if (is_warm_boot()) { |
aade2004 | 389 | /* enter self-refresh */ |
a7787b78 | 390 | setbits_be32(&ddr->sdram_cfg_2, SDRAM_CFG2_FRC_SR); |
aade2004 TY |
391 | /* do board specific memory setup */ |
392 | board_mem_sleep_setup(); | |
aade2004 | 393 | temp_sdram_cfg = (in_be32(&ddr->sdram_cfg) | SDRAM_CFG_BI); |
a7787b78 | 394 | } else |
aade2004 TY |
395 | #endif |
396 | temp_sdram_cfg = (in_be32(&ddr->sdram_cfg) & ~SDRAM_CFG_BI); | |
a7787b78 TY |
397 | |
398 | /* Let the controller go */ | |
e1be0d25 | 399 | out_be32(&ddr->sdram_cfg, temp_sdram_cfg | SDRAM_CFG_MEM_EN); |
fa8d23c0 | 400 | asm volatile("sync;isync"); |
2a6c2d7a | 401 | |
f31cfd19 YS |
402 | total_gb_size_per_controller = 0; |
403 | for (i = 0; i < CONFIG_CHIP_SELECTS_PER_CTRL; i++) { | |
404 | if (!(regs->cs[i].config & 0x80000000)) | |
405 | continue; | |
406 | total_gb_size_per_controller += 1 << ( | |
407 | ((regs->cs[i].config >> 14) & 0x3) + 2 + | |
408 | ((regs->cs[i].config >> 8) & 0x7) + 12 + | |
409 | ((regs->cs[i].config >> 0) & 0x7) + 8 + | |
410 | 3 - ((regs->ddr_sdram_cfg >> 19) & 0x3) - | |
411 | 26); /* minus 26 (count of 64M) */ | |
412 | } | |
413 | if (fsl_ddr_get_intl3r() & 0x80000000) /* 3-way interleaving */ | |
414 | total_gb_size_per_controller *= 3; | |
415 | else if (regs->cs[0].config & 0x20000000) /* 2-way interleaving */ | |
416 | total_gb_size_per_controller <<= 1; | |
417 | /* | |
418 | * total memory / bus width = transactions needed | |
419 | * transactions needed / data rate = seconds | |
420 | * to add plenty of buffer, double the time | |
421 | * For example, 2GB on 666MT/s 64-bit bus takes about 402ms | |
422 | * Let's wait for 800ms | |
423 | */ | |
424 | bus_width = 3 - ((ddr->sdram_cfg & SDRAM_CFG_DBW_MASK) | |
425 | >> SDRAM_CFG_DBW_SHIFT); | |
426 | timeout = ((total_gb_size_per_controller << (6 - bus_width)) * 100 / | |
03e664d8 | 427 | (get_ddr_freq(ctrl_num) >> 20)) << 1; |
23028d69 | 428 | #ifdef CONFIG_SYS_FSL_ERRATUM_DDR111_DDR134 |
f31cfd19 | 429 | timeout_save = timeout; |
23028d69 | 430 | #endif |
f31cfd19 YS |
431 | total_gb_size_per_controller >>= 4; /* shift down to gb size */ |
432 | debug("total %d GB\n", total_gb_size_per_controller); | |
433 | debug("Need to wait up to %d * 10ms\n", timeout); | |
434 | ||
2a6c2d7a | 435 | /* Poll DDR_SDRAM_CFG_2[D_INIT] bit until auto-data init is done. */ |
f31cfd19 YS |
436 | while ((in_be32(&ddr->sdram_cfg_2) & SDRAM_CFG2_D_INIT) && |
437 | (timeout >= 0)) { | |
2a6c2d7a | 438 | udelay(10000); /* throttle polling rate */ |
f31cfd19 YS |
439 | timeout--; |
440 | } | |
441 | ||
442 | if (timeout <= 0) | |
443 | printf("Waiting for D_INIT timeout. Memory may not work.\n"); | |
91671913 YS |
444 | |
445 | #ifdef CONFIG_SYS_FSL_ERRATUM_DDR111_DDR134 | |
446 | /* continue this workaround */ | |
447 | ||
448 | /* 4. Clear DEBUG3[21] */ | |
449 | clrbits_be32(&ddr->debug[2], 0x400); | |
450 | debug("Clearing D3[21] to 0x%08x\n", in_be32(&ddr->debug[2])); | |
451 | ||
452 | /* DDR134 workaround starts */ | |
453 | /* A: Clear sdram_cfg_2[odt_cfg] */ | |
454 | clrbits_be32(&ddr->sdram_cfg_2, SDRAM_CFG2_ODT_CFG_MASK); | |
455 | debug("Clearing SDRAM_CFG2[ODT_CFG] to 0x%08x\n", | |
456 | in_be32(&ddr->sdram_cfg_2)); | |
457 | ||
458 | /* B: Set DEBUG1[15] */ | |
459 | setbits_be32(&ddr->debug[0], 0x10000); | |
460 | debug("Setting D1[15] to 0x%08x\n", in_be32(&ddr->debug[0])); | |
461 | ||
462 | /* C: Set timing_cfg_2[cpo] to 0b11111 */ | |
463 | setbits_be32(&ddr->timing_cfg_2, TIMING_CFG_2_CPO_MASK); | |
464 | debug("Setting TMING_CFG_2[CPO] to 0x%08x\n", | |
465 | in_be32(&ddr->timing_cfg_2)); | |
466 | ||
467 | /* D: Set D6 to 0x9f9f9f9f */ | |
468 | out_be32(&ddr->debug[5], 0x9f9f9f9f); | |
469 | debug("Setting D6 to 0x%08x\n", in_be32(&ddr->debug[5])); | |
470 | ||
471 | /* E: Set D7 to 0x9f9f9f9f */ | |
472 | out_be32(&ddr->debug[6], 0x9f9f9f9f); | |
473 | debug("Setting D7 to 0x%08x\n", in_be32(&ddr->debug[6])); | |
474 | ||
475 | /* F: Set D2[20] */ | |
476 | setbits_be32(&ddr->debug[1], 0x800); | |
477 | debug("Setting D2[20] to 0x%08x\n", in_be32(&ddr->debug[1])); | |
478 | ||
479 | /* G: Poll on D2[20] until cleared */ | |
480 | while (in_be32(&ddr->debug[1]) & 0x800) | |
481 | udelay(10000); /* throttle polling rate */ | |
482 | ||
483 | /* H: Clear D1[15] */ | |
484 | clrbits_be32(&ddr->debug[0], 0x10000); | |
485 | debug("Setting D1[15] to 0x%08x\n", in_be32(&ddr->debug[0])); | |
486 | ||
487 | /* I: Set sdram_cfg_2[odt_cfg] */ | |
488 | setbits_be32(&ddr->sdram_cfg_2, | |
489 | regs->ddr_sdram_cfg_2 & SDRAM_CFG2_ODT_CFG_MASK); | |
490 | debug("Setting sdram_cfg_2 to 0x%08x\n", in_be32(&ddr->sdram_cfg_2)); | |
491 | ||
492 | /* Continuing with the DDR111 workaround */ | |
493 | /* 5. Set D2[21] */ | |
494 | setbits_be32(&ddr->debug[1], 0x400); | |
495 | debug("Setting D2[21] to 0x%08x\n", in_be32(&ddr->debug[1])); | |
496 | ||
497 | /* 6. Poll D2[21] until its cleared */ | |
498 | while (in_be32(&ddr->debug[1]) & 0x400) | |
499 | udelay(10000); /* throttle polling rate */ | |
500 | ||
f31cfd19 YS |
501 | /* 7. Wait for state machine 2nd run, roughly 400ms/GB */ |
502 | debug("Wait for %d * 10ms\n", timeout_save); | |
503 | udelay(timeout_save * 10000); | |
91671913 YS |
504 | |
505 | /* 8. Set sdram_cfg_2[dinit] if options requires */ | |
506 | setbits_be32(&ddr->sdram_cfg_2, | |
507 | regs->ddr_sdram_cfg_2 & SDRAM_CFG2_D_INIT); | |
508 | debug("Setting sdram_cfg_2 to 0x%08x\n", in_be32(&ddr->sdram_cfg_2)); | |
509 | ||
510 | /* 9. Poll until dinit is cleared */ | |
f31cfd19 YS |
511 | timeout = timeout_save; |
512 | debug("Need to wait up to %d * 10ms\n", timeout); | |
513 | while ((in_be32(&ddr->sdram_cfg_2) & SDRAM_CFG2_D_INIT) && | |
514 | (timeout >= 0)) { | |
515 | udelay(10000); /* throttle polling rate */ | |
516 | timeout--; | |
517 | } | |
518 | ||
519 | if (timeout <= 0) | |
520 | printf("Waiting for D_INIT timeout. Memory may not work.\n"); | |
91671913 YS |
521 | |
522 | /* 10. Clear EEBACR[3] */ | |
523 | clrbits_be32(&ecm->eebacr, 10000000); | |
524 | debug("Clearing EEBACR[3] to 0x%08x\n", in_be32(&ecm->eebacr)); | |
eb672e92 YS |
525 | |
526 | if (csn != -1) { | |
527 | csn_bnds_t = (unsigned int *) ®s->cs[csn].bnds; | |
528 | *csn_bnds_t = csn_bnds_backup; | |
529 | debug("Change cs%d_bnds back to 0x%08x\n", | |
530 | csn, regs->cs[csn].bnds); | |
531 | setbits_be32(&ddr->sdram_cfg, 0x2); /* MEM_HALT */ | |
532 | switch (csn) { | |
533 | case 0: | |
534 | out_be32(&ddr->cs0_bnds, regs->cs[csn].bnds); | |
535 | break; | |
536 | case 1: | |
537 | out_be32(&ddr->cs1_bnds, regs->cs[csn].bnds); | |
538 | break; | |
03e664d8 | 539 | #if CONFIG_CHIP_SELECTS_PER_CTRL > 2 |
eb672e92 YS |
540 | case 2: |
541 | out_be32(&ddr->cs2_bnds, regs->cs[csn].bnds); | |
542 | break; | |
543 | case 3: | |
544 | out_be32(&ddr->cs3_bnds, regs->cs[csn].bnds); | |
545 | break; | |
03e664d8 | 546 | #endif |
eb672e92 YS |
547 | } |
548 | clrbits_be32(&ddr->sdram_cfg, 0x2); | |
549 | } | |
91671913 | 550 | #endif /* CONFIG_SYS_FSL_ERRATUM_DDR111_DDR134 */ |
aade2004 | 551 | #ifdef CONFIG_DEEP_SLEEP |
a7787b78 | 552 | if (is_warm_boot()) |
aade2004 | 553 | /* exit self-refresh */ |
a7787b78 | 554 | clrbits_be32(&ddr->sdram_cfg_2, SDRAM_CFG2_FRC_SR); |
aade2004 | 555 | #endif |
2a6c2d7a | 556 | } |