]> git.ipfire.org Git - people/ms/u-boot.git/blame - arch/powerpc/cpu/ppc4xx/sdram.c
Add GPL-2.0+ SPDX-License-Identifier to source files
[people/ms/u-boot.git] / arch / powerpc / cpu / ppc4xx / sdram.c
CommitLineData
c609719b 1/*
5fb692ca 2 * (C) Copyright 2005-2007
5568e613
SR
3 * Stefan Roese, DENX Software Engineering, sr@denx.de.
4 *
62534beb
SR
5 * (C) Copyright 2006
6 * DAVE Srl <www.dave-tech.it>
7 *
de8d5a36 8 * (C) Copyright 2002-2004
c609719b
WD
9 * Stefan Roese, esd gmbh germany, stefan.roese@esd-electronics.com
10 *
1a459660 11 * SPDX-License-Identifier: GPL-2.0+
c609719b
WD
12 */
13
14#include <common.h>
b36df561 15#include <asm/ppc4xx.h>
c609719b 16#include <asm/processor.h>
62534beb 17#include "sdram.h"
c821b5f1 18#include "ecc.h"
c609719b 19
c609719b
WD
20#ifdef CONFIG_SDRAM_BANK0
21
5fb692ca 22#ifndef CONFIG_440
c609719b 23
6d0f6bcf 24#ifndef CONFIG_SYS_SDRAM_TABLE
de8d5a36 25sdram_conf_t mb0cf[] = {
cf48eb9a
WD
26 {(128 << 20), 13, 0x000A4001}, /* (0-128MB) Address Mode 3, 13x10(4) */
27 {(64 << 20), 13, 0x00084001}, /* (0-64MB) Address Mode 3, 13x9(4) */
28 {(32 << 20), 12, 0x00062001}, /* (0-32MB) Address Mode 2, 12x9(4) */
29 {(16 << 20), 12, 0x00046001}, /* (0-16MB) Address Mode 4, 12x8(4) */
30 {(4 << 20), 11, 0x00008001}, /* (0-4MB) Address Mode 5, 11x8(2) */
de8d5a36 31};
5568e613 32#else
6d0f6bcf 33sdram_conf_t mb0cf[] = CONFIG_SYS_SDRAM_TABLE;
5568e613
SR
34#endif
35
cf48eb9a 36#define N_MB0CF (sizeof(mb0cf) / sizeof(mb0cf[0]))
c609719b 37
6d0f6bcf 38#ifdef CONFIG_SYS_SDRAM_CASL
62534beb
SR
39static ulong ns2clks(ulong ns)
40{
41 ulong bus_period_x_10 = ONE_BILLION / (get_bus_freq(0) / 10);
42
43 return ((ns * 10) + bus_period_x_10) / bus_period_x_10;
44}
6d0f6bcf 45#endif /* CONFIG_SYS_SDRAM_CASL */
62534beb
SR
46
47static ulong compute_sdtr1(ulong speed)
48{
6d0f6bcf 49#ifdef CONFIG_SYS_SDRAM_CASL
cf48eb9a
WD
50 ulong tmp;
51 ulong sdtr1 = 0;
52
53 /* CASL */
6d0f6bcf 54 if (CONFIG_SYS_SDRAM_CASL < 2)
cf48eb9a
WD
55 sdtr1 |= (1 << SDRAM0_TR_CASL);
56 else
6d0f6bcf 57 if (CONFIG_SYS_SDRAM_CASL > 4)
cf48eb9a
WD
58 sdtr1 |= (3 << SDRAM0_TR_CASL);
59 else
6d0f6bcf 60 sdtr1 |= ((CONFIG_SYS_SDRAM_CASL-1) << SDRAM0_TR_CASL);
cf48eb9a
WD
61
62 /* PTA */
6d0f6bcf 63 tmp = ns2clks(CONFIG_SYS_SDRAM_PTA);
cf48eb9a
WD
64 if ((tmp >= 2) && (tmp <= 4))
65 sdtr1 |= ((tmp-1) << SDRAM0_TR_PTA);
66 else
67 sdtr1 |= ((4-1) << SDRAM0_TR_PTA);
68
69 /* CTP */
6d0f6bcf 70 tmp = ns2clks(CONFIG_SYS_SDRAM_CTP);
cf48eb9a
WD
71 if ((tmp >= 2) && (tmp <= 4))
72 sdtr1 |= ((tmp-1) << SDRAM0_TR_CTP);
73 else
74 sdtr1 |= ((4-1) << SDRAM0_TR_CTP);
75
76 /* LDF */
6d0f6bcf 77 tmp = ns2clks(CONFIG_SYS_SDRAM_LDF);
cf48eb9a
WD
78 if ((tmp >= 2) && (tmp <= 4))
79 sdtr1 |= ((tmp-1) << SDRAM0_TR_LDF);
80 else
81 sdtr1 |= ((2-1) << SDRAM0_TR_LDF);
82
83 /* RFTA */
6d0f6bcf 84 tmp = ns2clks(CONFIG_SYS_SDRAM_RFTA);
cf48eb9a
WD
85 if ((tmp >= 4) && (tmp <= 10))
86 sdtr1 |= ((tmp-4) << SDRAM0_TR_RFTA);
87 else
88 sdtr1 |= ((10-4) << SDRAM0_TR_RFTA);
89
90 /* RCD */
6d0f6bcf 91 tmp = ns2clks(CONFIG_SYS_SDRAM_RCD);
cf48eb9a
WD
92 if ((tmp >= 2) && (tmp <= 4))
93 sdtr1 |= ((tmp-1) << SDRAM0_TR_RCD);
94 else
95 sdtr1 |= ((4-1) << SDRAM0_TR_RCD);
96
97 return sdtr1;
6d0f6bcf 98#else /* CONFIG_SYS_SDRAM_CASL */
cf48eb9a
WD
99 /*
100 * If no values are configured in the board config file
101 * use the default values, which seem to be ok for most
102 * boards.
103 *
104 * REMARK:
105 * For new board ports we strongly recommend to define the
106 * correct values for the used SDRAM chips in your board
107 * config file (see PPChameleonEVB.h)
108 */
109 if (speed > 100000000) {
110 /*
111 * 133 MHz SDRAM
112 */
113 return 0x01074015;
114 } else {
115 /*
116 * default: 100 MHz SDRAM
117 */
118 return 0x0086400d;
119 }
6d0f6bcf 120#endif /* CONFIG_SYS_SDRAM_CASL */
62534beb
SR
121}
122
123/* refresh is expressed in ms */
124static ulong compute_rtr(ulong speed, ulong rows, ulong refresh)
125{
6d0f6bcf 126#ifdef CONFIG_SYS_SDRAM_CASL
cf48eb9a 127 ulong tmp;
62534beb 128
cf48eb9a
WD
129 tmp = ((refresh*1000*1000) / (1 << rows)) * (speed / 1000);
130 tmp /= 1000000;
62534beb 131
cf48eb9a 132 return ((tmp & 0x00003FF8) << 16);
6d0f6bcf 133#else /* CONFIG_SYS_SDRAM_CASL */
cf48eb9a
WD
134 if (speed > 100000000) {
135 /*
136 * 133 MHz SDRAM
137 */
62534beb 138 return 0x07f00000;
cf48eb9a
WD
139 } else {
140 /*
141 * default: 100 MHz SDRAM
142 */
62534beb 143 return 0x05f00000;
cf48eb9a 144 }
6d0f6bcf 145#endif /* CONFIG_SYS_SDRAM_CASL */
62534beb
SR
146}
147
5568e613
SR
148/*
149 * Autodetect onboard SDRAM on 405 platforms
150 */
9973e3c6 151phys_size_t initdram(int board_type)
c609719b 152{
62534beb 153 ulong speed;
c609719b 154 ulong sdtr1;
de8d5a36 155 int i;
c609719b 156
cf48eb9a
WD
157 /*
158 * Determine SDRAM speed
159 */
160 speed = get_bus_freq(0); /* parameter not used on ppc4xx */
62534beb 161
cf48eb9a
WD
162 /*
163 * sdtr1 (register SDRAM0_TR) must take into account timings listed
164 * in SDRAM chip datasheet. rtr (register SDRAM0_RTR) must take into
165 * account actual SDRAM size. So we can set up sdtr1 according to what
166 * is specified in board configuration file while rtr dependds on SDRAM
167 * size we are assuming before detection.
168 */
169 sdtr1 = compute_sdtr1(speed);
c609719b 170
de8d5a36 171 for (i=0; i<N_MB0CF; i++) {
6177445d 172 /*
de8d5a36 173 * Disable memory controller.
6177445d 174 */
95b602ba 175 mtsdram(SDRAM0_CFG, 0x00000000);
e5ad56b1 176
c609719b 177 /*
de8d5a36 178 * Set MB0CF for bank 0.
c609719b 179 */
95b602ba
SR
180 mtsdram(SDRAM0_B0CR, mb0cf[i].reg);
181 mtsdram(SDRAM0_TR, sdtr1);
182 mtsdram(SDRAM0_RTR, compute_rtr(speed, mb0cf[i].rows, 64));
e5ad56b1 183
de8d5a36 184 udelay(200);
c609719b 185
c609719b 186 /*
de8d5a36
SR
187 * Set memory controller options reg, MCOPT1.
188 * Set DC_EN to '1' and BRD_PRF to '01' for 16 byte PLB Burst
189 * read/prefetch.
c609719b 190 */
95b602ba 191 mtsdram(SDRAM0_CFG, 0x80800000);
c609719b 192
de8d5a36 193 udelay(10000);
c609719b 194
de8d5a36 195 if (get_ram_size(0, mb0cf[i].size) == mb0cf[i].size) {
7bf5ecfa
SR
196 phys_size_t size = mb0cf[i].size;
197
de8d5a36 198 /*
d4024bb7
JO
199 * OK, size detected. Enable second bank if
200 * defined (assumes same type as bank 0)
de8d5a36 201 */
d4024bb7 202#ifdef CONFIG_SDRAM_BANK1
95b602ba
SR
203 mtsdram(SDRAM0_CFG, 0x00000000);
204 mtsdram(SDRAM0_B1CR, mb0cf[i].size | mb0cf[i].reg);
205 mtsdram(SDRAM0_CFG, 0x80800000);
d4024bb7 206 udelay(10000);
779e9751
SR
207
208 /*
209 * Check if 2nd bank is really available.
210 * If the size not equal to the size of the first
211 * bank, then disable the 2nd bank completely.
212 */
213 if (get_ram_size((long *)mb0cf[i].size, mb0cf[i].size) !=
214 mb0cf[i].size) {
95b602ba
SR
215 mtsdram(SDRAM0_B1CR, 0);
216 mtsdram(SDRAM0_CFG, 0);
7bf5ecfa
SR
217 } else {
218 /*
219 * We have two identical banks, so the size
220 * is twice the bank size
221 */
222 size = 2 * size;
779e9751 223 }
d4024bb7 224#endif
bbeff30c
SR
225
226 /*
227 * OK, size detected -> all done
228 */
7bf5ecfa 229 return size;
de8d5a36 230 }
6177445d 231 }
bbeff30c
SR
232
233 return 0;
c609719b
WD
234}
235
5568e613
SR
236#else /* CONFIG_440 */
237
5fb692ca
SR
238/*
239 * Define some default values. Those can be overwritten in the
240 * board config file.
241 */
242
6d0f6bcf 243#ifndef CONFIG_SYS_SDRAM_TABLE
5fb692ca
SR
244sdram_conf_t mb0cf[] = {
245 {(256 << 20), 13, 0x000C4001}, /* 256MB mode 3, 13x10(4) */
3943d2ff 246 {(128 << 20), 13, 0x000A4001}, /* 128MB mode 3, 13x10(4) */
5fb692ca
SR
247 {(64 << 20), 12, 0x00082001} /* 64MB mode 2, 12x9(4) */
248};
249#else
6d0f6bcf 250sdram_conf_t mb0cf[] = CONFIG_SYS_SDRAM_TABLE;
5fb692ca
SR
251#endif
252
6d0f6bcf
JCPV
253#ifndef CONFIG_SYS_SDRAM0_TR0
254#define CONFIG_SYS_SDRAM0_TR0 0x41094012
5fb692ca
SR
255#endif
256
3943d2ff
DE
257#ifndef CONFIG_SYS_SDRAM0_WDDCTR
258#define CONFIG_SYS_SDRAM0_WDDCTR 0x00000000 /* wrcp=0 dcd=0 */
259#endif
260
261#ifndef CONFIG_SYS_SDRAM0_RTR
262#define CONFIG_SYS_SDRAM0_RTR 0x04100000 /* 7.8us @ 133MHz PLB */
263#endif
264
265#ifndef CONFIG_SYS_SDRAM0_CFG0
266#define CONFIG_SYS_SDRAM0_CFG0 0x82000000 /* DCEN=1, PMUD=0, 64-bit */
267#endif
268
5fb692ca
SR
269#define N_MB0CF (sizeof(mb0cf) / sizeof(mb0cf[0]))
270
62534beb
SR
271#define NUM_TRIES 64
272#define NUM_READS 10
273
274static void sdram_tr1_set(int ram_address, int* tr1_value)
275{
276 int i;
277 int j, k;
278 volatile unsigned int* ram_pointer = (unsigned int *)ram_address;
279 int first_good = -1, last_bad = 0x1ff;
280
281 unsigned long test[NUM_TRIES] = {
282 0x00000000, 0x00000000, 0xFFFFFFFF, 0xFFFFFFFF,
283 0x00000000, 0x00000000, 0xFFFFFFFF, 0xFFFFFFFF,
284 0xFFFFFFFF, 0xFFFFFFFF, 0x00000000, 0x00000000,
285 0xFFFFFFFF, 0xFFFFFFFF, 0x00000000, 0x00000000,
286 0xAAAAAAAA, 0xAAAAAAAA, 0x55555555, 0x55555555,
287 0xAAAAAAAA, 0xAAAAAAAA, 0x55555555, 0x55555555,
288 0x55555555, 0x55555555, 0xAAAAAAAA, 0xAAAAAAAA,
289 0x55555555, 0x55555555, 0xAAAAAAAA, 0xAAAAAAAA,
290 0xA5A5A5A5, 0xA5A5A5A5, 0x5A5A5A5A, 0x5A5A5A5A,
291 0xA5A5A5A5, 0xA5A5A5A5, 0x5A5A5A5A, 0x5A5A5A5A,
292 0x5A5A5A5A, 0x5A5A5A5A, 0xA5A5A5A5, 0xA5A5A5A5,
293 0x5A5A5A5A, 0x5A5A5A5A, 0xA5A5A5A5, 0xA5A5A5A5,
294 0xAA55AA55, 0xAA55AA55, 0x55AA55AA, 0x55AA55AA,
295 0xAA55AA55, 0xAA55AA55, 0x55AA55AA, 0x55AA55AA,
296 0x55AA55AA, 0x55AA55AA, 0xAA55AA55, 0xAA55AA55,
297 0x55AA55AA, 0x55AA55AA, 0xAA55AA55, 0xAA55AA55 };
298
299 /* go through all possible SDRAM0_TR1[RDCT] values */
300 for (i=0; i<=0x1ff; i++) {
301 /* set the current value for TR1 */
95b602ba 302 mtsdram(SDRAM0_TR1, (0x80800800 | i));
62534beb
SR
303
304 /* write values */
305 for (j=0; j<NUM_TRIES; j++) {
306 ram_pointer[j] = test[j];
307
308 /* clear any cache at ram location */
309 __asm__("dcbf 0,%0": :"r" (&ram_pointer[j]));
310 }
311
312 /* read values back */
313 for (j=0; j<NUM_TRIES; j++) {
314 for (k=0; k<NUM_READS; k++) {
315 /* clear any cache at ram location */
316 __asm__("dcbf 0,%0": :"r" (&ram_pointer[j]));
317
318 if (ram_pointer[j] != test[j])
319 break;
320 }
321
322 /* read error */
323 if (k != NUM_READS)
324 break;
325 }
326
327 /* we have a SDRAM0_TR1[RDCT] that is part of the window */
328 if (j == NUM_TRIES) {
329 if (first_good == -1)
330 first_good = i; /* found beginning of window */
331 } else { /* bad read */
332 /* if we have not had a good read then don't care */
333 if (first_good != -1) {
334 /* first failure after a good read */
335 last_bad = i-1;
336 break;
337 }
338 }
339 }
340
341 /* return the current value for TR1 */
342 *tr1_value = (first_good + last_bad) / 2;
343}
344
5568e613
SR
345/*
346 * Autodetect onboard DDR SDRAM on 440 platforms
347 *
348 * NOTE: Some of the hardcoded values are hardware dependant,
cf48eb9a
WD
349 * so this should be extended for other future boards
350 * using this routine!
5568e613 351 */
9973e3c6 352phys_size_t initdram(int board_type)
5568e613
SR
353{
354 int i;
62534beb 355 int tr1_bank1;
5568e613 356
5fb692ca
SR
357#if defined(CONFIG_440GX) || defined(CONFIG_440EP) || \
358 defined(CONFIG_440GR) || defined(CONFIG_440SP)
899620c2
SR
359 /*
360 * Soft-reset SDRAM controller.
361 */
d1c3b275
SR
362 mtsdr(SDR0_SRST, SDR0_SRST_DMC);
363 mtsdr(SDR0_SRST, 0x00000000);
899620c2
SR
364#endif
365
5568e613
SR
366 for (i=0; i<N_MB0CF; i++) {
367 /*
368 * Disable memory controller.
369 */
95b602ba 370 mtsdram(SDRAM0_CFG0, 0x00000000);
5568e613
SR
371
372 /*
373 * Setup some default
374 */
95b602ba
SR
375 mtsdram(SDRAM0_UABBA, 0x00000000); /* ubba=0 (default) */
376 mtsdram(SDRAM0_SLIO, 0x00000000); /* rdre=0 wrre=0 rarw=0 */
377 mtsdram(SDRAM0_DEVOPT, 0x00000000); /* dll=0 ds=0 (normal) */
378 mtsdram(SDRAM0_WDDCTR, CONFIG_SYS_SDRAM0_WDDCTR);
379 mtsdram(SDRAM0_CLKTR, 0x40000000); /* clkp=1 (90 deg wr) dcdt=0 */
5568e613
SR
380
381 /*
382 * Following for CAS Latency = 2.5 @ 133 MHz PLB
383 */
95b602ba
SR
384 mtsdram(SDRAM0_B0CR, mb0cf[i].reg);
385 mtsdram(SDRAM0_TR0, CONFIG_SYS_SDRAM0_TR0);
386 mtsdram(SDRAM0_TR1, 0x80800800); /* SS=T2 SL=STAGE 3 CD=1 CT=0x00*/
387 mtsdram(SDRAM0_RTR, CONFIG_SYS_SDRAM0_RTR);
388 mtsdram(SDRAM0_CFG1, 0x00000000); /* Self-refresh exit, disable PM*/
5568e613
SR
389 udelay(400); /* Delay 200 usecs (min) */
390
391 /*
392 * Enable the controller, then wait for DCEN to complete
393 */
95b602ba 394 mtsdram(SDRAM0_CFG0, CONFIG_SYS_SDRAM0_CFG0);
5568e613
SR
395 udelay(10000);
396
397 if (get_ram_size(0, mb0cf[i].size) == mb0cf[i].size) {
3943d2ff 398 phys_size_t size = mb0cf[i].size;
62534beb
SR
399 /*
400 * Optimize TR1 to current hardware environment
401 */
402 sdram_tr1_set(0x00000000, &tr1_bank1);
95b602ba 403 mtsdram(SDRAM0_TR1, (tr1_bank1 | 0x80800800));
62534beb 404
3943d2ff
DE
405
406 /*
407 * OK, size detected. Enable second bank if
408 * defined (assumes same type as bank 0)
409 */
410#ifdef CONFIG_SDRAM_BANK1
95b602ba
SR
411 mtsdram(SDRAM0_CFG0, 0);
412 mtsdram(SDRAM0_B1CR, mb0cf[i].size | mb0cf[i].reg);
413 mtsdram(SDRAM0_CFG0, CONFIG_SYS_SDRAM0_CFG0);
3943d2ff
DE
414 udelay(10000);
415
416 /*
417 * Check if 2nd bank is really available.
418 * If the size not equal to the size of the first
419 * bank, then disable the 2nd bank completely.
420 */
421 if (get_ram_size((long *)mb0cf[i].size, mb0cf[i].size)
422 != mb0cf[i].size) {
95b602ba
SR
423 mtsdram(SDRAM0_CFG0, 0);
424 mtsdram(SDRAM0_B1CR, 0);
425 mtsdram(SDRAM0_CFG0, CONFIG_SYS_SDRAM0_CFG0);
3943d2ff
DE
426 udelay(10000);
427 } else {
428 /*
429 * We have two identical banks, so the size
430 * is twice the bank size
431 */
432 size = 2 * size;
433 }
434#endif
435
62534beb 436#ifdef CONFIG_SDRAM_ECC
3943d2ff 437 ecc_init(0, size);
62534beb
SR
438#endif
439
5568e613
SR
440 /*
441 * OK, size detected -> all done
442 */
3943d2ff 443 return size;
5568e613
SR
444 }
445 }
446
447 return 0; /* nothing found ! */
448}
449
450#endif /* CONFIG_440 */
451
c609719b 452#endif /* CONFIG_SDRAM_BANK0 */