]>
Commit | Line | Data |
---|---|---|
afd7f3d0 WD |
1 | /* |
2 | * (C) Copyright 2000 | |
3 | * Sysgo Real-Time Solutions, GmbH <www.elinos.com> | |
4 | * Marius Groeger <[email protected]> | |
5 | * | |
6 | * (C) Copyright 2001 | |
7 | * Advent Networks, Inc. <http://www.adventnetworks.com> | |
8 | * Jay Monkman <[email protected]> | |
9 | * | |
10 | * (C) Copyright 2001 | |
11 | * Advent Networks, Inc. <http://www.adventnetworks.com> | |
12 | * Oliver Brown <[email protected]> | |
13 | * | |
14 | * See file CREDITS for list of people who contributed to this | |
15 | * project. | |
16 | * | |
17 | * This program is free software; you can redistribute it and/or | |
18 | * modify it under the terms of the GNU General Public License as | |
19 | * published by the Free Software Foundation; either version 2 of | |
20 | * the License, or (at your option) any later version. | |
21 | * | |
22 | * This program is distributed in the hope that it will be useful, | |
23 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
24 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
25 | * GNU General Public License for more details. | |
26 | * | |
27 | * You should have received a copy of the GNU General Public License | |
28 | * along with this program; if not, write to the Free Software | |
29 | * Foundation, Inc., 59 Temple Place, Suite 330, Boston, | |
30 | * MA 02111-1307 USA | |
31 | */ | |
32 | ||
33 | /*********************************************************************/ | |
34 | /* DESCRIPTION: | |
35 | * This file contains the board routines for the GW8260 board. | |
36 | * | |
37 | * MODULE DEPENDENCY: | |
38 | * None | |
39 | * | |
40 | * RESTRICTIONS/LIMITATIONS: | |
41 | * None | |
42 | * | |
43 | * Copyright (c) 2001, Advent Networks, Inc. | |
44 | */ | |
45 | /*********************************************************************/ | |
46 | ||
47 | #include <common.h> | |
48 | #include <ioports.h> | |
49 | #include <mpc8260.h> | |
50 | ||
51 | /* | |
52 | * I/O Port configuration table | |
53 | * | |
54 | */ | |
55 | const iop_conf_t iop_conf_tab[4][32] = { | |
56 | ||
57 | /* Port A configuration */ | |
58 | { /* conf ppar psor pdir podr pdat */ | |
59 | /* PA31 */ { 1, 0, 0, 1, 0, 0 }, /* TP14 */ | |
60 | /* PA30 */ { 1, 1, 1, 1, 0, 0 }, /* US_RTS */ | |
61 | /* PA29 */ { 1, 0, 0, 1, 0, 1 }, /* LSSI_DATA */ | |
62 | /* PA28 */ { 1, 0, 0, 1, 0, 1 }, /* LSSI_CLK */ | |
63 | /* PA27 */ { 1, 0, 0, 1, 0, 0 }, /* TP12 */ | |
64 | /* PA26 */ { 1, 0, 0, 0, 0, 0 }, /* IO_STATUS */ | |
65 | /* PA25 */ { 1, 0, 0, 0, 0, 0 }, /* IO_CLOCK */ | |
66 | /* PA24 */ { 1, 0, 0, 0, 0, 0 }, /* IO_CONFIG */ | |
67 | /* PA23 */ { 1, 0, 0, 0, 0, 0 }, /* IO_DONE */ | |
68 | /* PA22 */ { 1, 0, 0, 0, 0, 0 }, /* IO_DATA */ | |
69 | /* PA21 */ { 1, 1, 0, 1, 0, 0 }, /* US_TXD3 */ | |
70 | /* PA20 */ { 1, 1, 0, 1, 0, 0 }, /* US_TXD2 */ | |
71 | /* PA19 */ { 1, 1, 0, 1, 0, 0 }, /* US_TXD1 */ | |
72 | /* PA18 */ { 1, 1, 0, 1, 0, 0 }, /* US_TXD0 */ | |
73 | /* PA17 */ { 1, 1, 0, 0, 0, 0 }, /* DS_RXD0 */ | |
74 | /* PA16 */ { 1, 1, 0, 0, 0, 0 }, /* DS_RXD1 */ | |
75 | /* PA15 */ { 1, 1, 0, 0, 0, 0 }, /* DS_RXD2 */ | |
76 | /* PA14 */ { 1, 1, 0, 0, 0, 0 }, /* DS_RXD3 */ | |
77 | /* PA13 */ { 1, 0, 0, 1, 0, 0 }, /* SPARE7 */ | |
78 | /* PA12 */ { 1, 0, 0, 1, 0, 0 }, /* SPARE6 */ | |
79 | /* PA11 */ { 1, 0, 0, 1, 0, 0 }, /* SPARE5 */ | |
80 | /* PA10 */ { 1, 0, 0, 1, 0, 0 }, /* SPARE4 */ | |
81 | /* PA9 */ { 1, 0, 0, 1, 0, 0 }, /* SPARE3 */ | |
82 | /* PA8 */ { 1, 0, 0, 1, 0, 0 }, /* SPARE2 */ | |
83 | /* PA7 */ { 1, 0, 0, 0, 0, 0 }, /* LSSI_IN */ | |
84 | /* PA6 */ { 1, 0, 0, 1, 0, 0 }, /* SPARE0 */ | |
85 | /* PA5 */ { 1, 0, 0, 1, 0, 0 }, /* DEMOD_RESET_ */ | |
86 | /* PA4 */ { 1, 0, 0, 1, 0, 0 }, /* MOD_RESET_ */ | |
87 | /* PA3 */ { 1, 0, 0, 1, 0, 0 }, /* IO_RESET */ | |
88 | /* PA2 */ { 1, 0, 0, 1, 0, 0 }, /* TX_ENABLE */ | |
89 | /* PA1 */ { 1, 0, 0, 0, 0, 0 }, /* RX_LOCK */ | |
90 | /* PA0 */ { 1, 0, 0, 1, 0, 1 } /* MPC_RESET_ */ | |
91 | }, | |
92 | ||
93 | /* Port B configuration */ | |
94 | { /* conf ppar psor pdir podr pdat */ | |
95 | /* PB31 */ { 1, 1, 0, 1, 0, 0 }, /* FETH0_TX_ER */ | |
96 | /* PB30 */ { 1, 1, 0, 0, 0, 0 }, /* FETH0_RX_DV */ | |
97 | /* PB29 */ { 1, 1, 1, 1, 0, 0 }, /* FETH0_TX_EN */ | |
98 | /* PB28 */ { 1, 1, 0, 0, 0, 0 }, /* FETH0_RX_ER */ | |
99 | /* PB27 */ { 1, 1, 0, 0, 0, 0 }, /* FETH0_COL */ | |
100 | /* PB26 */ { 1, 1, 0, 0, 0, 0 }, /* FETH0_CRS */ | |
101 | /* PB25 */ { 1, 1, 0, 1, 0, 0 }, /* FETH0_TXD3 */ | |
102 | /* PB24 */ { 1, 1, 0, 1, 0, 0 }, /* FETH0_TXD2 */ | |
103 | /* PB23 */ { 1, 1, 0, 1, 0, 0 }, /* FETH0_TXD1 */ | |
104 | /* PB22 */ { 1, 1, 0, 1, 0, 0 }, /* FETH0_TXD0 */ | |
105 | /* PB21 */ { 1, 1, 0, 0, 0, 0 }, /* FETH0_RXD0 */ | |
106 | /* PB20 */ { 1, 1, 0, 0, 0, 0 }, /* FETH0_RXD1 */ | |
107 | /* PB19 */ { 1, 1, 0, 0, 0, 0 }, /* FETH0_RXD2 */ | |
108 | /* PB18 */ { 1, 1, 0, 0, 0, 0 }, /* FETH0_RXD3 */ | |
109 | /* PB17 */ { 1, 1, 0, 0, 0, 0 }, /* FETH1_RX_DV */ | |
110 | /* PB16 */ { 1, 1, 0, 0, 0, 0 }, /* FETH1_RX_ER */ | |
111 | /* PB15 */ { 1, 1, 0, 1, 0, 0 }, /* FETH1_TX_ER */ | |
112 | /* PB14 */ { 1, 1, 0, 1, 0, 0 }, /* FETH1_TX_EN */ | |
113 | /* PB13 */ { 1, 1, 0, 0, 0, 0 }, /* FETH1_COL */ | |
114 | /* PB12 */ { 1, 1, 0, 0, 0, 0 }, /* FETH1_CRS */ | |
115 | /* PB11 */ { 1, 1, 0, 0, 0, 0 }, /* FETH1_RXD3 */ | |
116 | /* PB10 */ { 1, 1, 0, 0, 0, 0 }, /* FETH1_RXD2 */ | |
117 | /* PB9 */ { 1, 1, 0, 0, 0, 0 }, /* FETH1_RXD1 */ | |
118 | /* PB8 */ { 1, 1, 0, 0, 0, 0 }, /* FETH1_RXD0 */ | |
119 | /* PB7 */ { 1, 1, 0, 1, 0, 0 }, /* FETH1_TXD0 */ | |
120 | /* PB6 */ { 1, 1, 0, 1, 0, 0 }, /* FETH1_TXD1 */ | |
121 | /* PB5 */ { 1, 1, 0, 1, 0, 0 }, /* FETH1_TXD2 */ | |
122 | /* PB4 */ { 1, 1, 0, 1, 0, 0 }, /* FETH1_TXD3 */ | |
123 | /* PB3 */ { 0, 0, 0, 0, 0, 0 }, /* pin doesn't exist */ | |
124 | /* PB2 */ { 0, 0, 0, 0, 0, 0 }, /* pin doesn't exist */ | |
125 | /* PB1 */ { 0, 0, 0, 0, 0, 0 }, /* pin doesn't exist */ | |
126 | /* PB0 */ { 0, 0, 0, 0, 0, 0 } /* pin doesn't exist */ | |
127 | }, | |
128 | ||
129 | /* Port C */ | |
130 | { /* conf ppar psor pdir podr pdat */ | |
131 | /* PC31 */ { 1, 0, 0, 1, 0, 1 }, /* FAST_RESET_ */ | |
132 | /* PC30 */ { 1, 0, 0, 1, 0, 1 }, /* FAST_PAUSE_ */ | |
133 | /* PC29 */ { 1, 0, 0, 1, 0, 0 }, /* FAST_SLEW1 */ | |
134 | /* PC28 */ { 1, 0, 0, 1, 0, 0 }, /* FAST_SLEW0 */ | |
135 | /* PC27 */ { 1, 0, 0, 1, 0, 0 }, /* TP13 */ | |
136 | /* PC26 */ { 1, 0, 0, 0, 0, 0 }, /* RXDECDFLG */ | |
137 | /* PC25 */ { 1, 0, 0, 0, 0, 0 }, /* RXACQFAIL */ | |
138 | /* PC24 */ { 1, 0, 0, 0, 0, 0 }, /* RXACQFLG */ | |
139 | /* PC23 */ { 1, 0, 0, 1, 0, 0 }, /* WD_TCL */ | |
140 | /* PC22 */ { 1, 0, 0, 1, 0, 0 }, /* WD_EN */ | |
141 | /* PC21 */ { 1, 0, 0, 1, 0, 0 }, /* US_TXCLK */ | |
142 | /* PC20 */ { 1, 0, 0, 0, 0, 0 }, /* DS_RXCLK */ | |
143 | /* PC19 */ { 1, 1, 0, 0, 0, 0 }, /* FETH0_RX_CLK */ | |
144 | /* PC18 */ { 1, 1, 0, 0, 0, 0 }, /* FETH0_TX_CLK */ | |
145 | /* PC17 */ { 1, 1, 0, 0, 0, 0 }, /* FETH1_RX_CLK */ | |
146 | /* PC16 */ { 1, 1, 0, 0, 0, 0 }, /* FETH1_TX_CLK */ | |
147 | /* PC15 */ { 1, 0, 0, 1, 0, 0 }, /* TX_SHUTDOWN_ */ | |
148 | /* PC14 */ { 1, 0, 0, 0, 0, 0 }, /* RS_232_DTR_ */ | |
149 | /* PC13 */ { 1, 0, 0, 0, 0, 0 }, /* TXERR */ | |
150 | /* PC12 */ { 1, 0, 0, 1, 0, 1 }, /* FETH1_MDDIS */ | |
151 | /* PC11 */ { 1, 0, 0, 1, 0, 1 }, /* FETH0_MDDIS */ | |
152 | /* PC10 */ { 1, 0, 0, 1, 0, 0 }, /* MDC */ | |
153 | /* PC9 */ { 1, 0, 0, 1, 1, 1 }, /* MDIO */ | |
154 | /* PC8 */ { 1, 0, 0, 1, 1, 1 }, /* SER_NUM */ | |
155 | /* PC7 */ { 1, 1, 0, 0, 0, 0 }, /* US_CTS */ | |
156 | /* PC6 */ { 1, 1, 0, 0, 0, 0 }, /* DS_CD_ */ | |
157 | /* PC5 */ { 1, 0, 0, 1, 0, 0 }, /* FETH1_PWRDWN */ | |
158 | /* PC4 */ { 1, 0, 0, 1, 0, 0 }, /* FETH0_PWRDWN */ | |
159 | /* PC3 */ { 1, 0, 0, 1, 0, 0 }, /* MPULED3 */ | |
160 | /* PC2 */ { 1, 0, 0, 1, 0, 0 }, /* MPULED2 */ | |
161 | /* PC1 */ { 1, 0, 0, 1, 0, 0 }, /* MPULED1 */ | |
162 | /* PC0 */ { 1, 0, 0, 1, 0, 1 }, /* MPULED0 */ | |
163 | }, | |
164 | ||
165 | /* Port D */ | |
166 | { /* conf ppar psor pdir podr pdat */ | |
167 | /* PD31 */ { 1, 0, 0, 0, 0, 0 }, /* not used */ | |
168 | /* PD30 */ { 1, 0, 0, 0, 0, 0 }, /* not used */ | |
169 | /* PD29 */ { 1, 0, 0, 0, 0, 0 }, /* not used */ | |
170 | /* PD28 */ { 1, 0, 0, 0, 0, 0 }, /* not used */ | |
171 | /* PD27 */ { 1, 0, 0, 0, 0, 0 }, /* not used */ | |
172 | /* PD26 */ { 1, 0, 0, 0, 0, 0 }, /* not used */ | |
173 | /* PD25 */ { 1, 0, 0, 0, 0, 0 }, /* not used */ | |
174 | /* PD24 */ { 1, 0, 0, 0, 0, 0 }, /* not used */ | |
175 | /* PD23 */ { 1, 0, 0, 0, 0, 0 }, /* not used */ | |
176 | /* PD22 */ { 1, 0, 0, 0, 0, 0 }, /* not used */ | |
177 | /* PD21 */ { 1, 0, 0, 0, 0, 0 }, /* not used */ | |
178 | /* PD20 */ { 1, 0, 0, 0, 0, 0 }, /* not used */ | |
179 | /* PD19 */ { 1, 1, 1, 0, 0, 0 }, /* not used */ | |
180 | /* PD18 */ { 1, 1, 1, 0, 0, 0 }, /* not used */ | |
181 | /* PD17 */ { 1, 1, 1, 0, 0, 0 }, /* not used */ | |
182 | /* PD16 */ { 1, 1, 1, 0, 0, 0 }, /* not used */ | |
183 | /* PD15 */ { 1, 1, 1, 0, 1, 1 }, /* SDRAM_SDA */ | |
184 | /* PD14 */ { 1, 1, 1, 0, 1, 1 }, /* SDRAM_SCL */ | |
185 | /* PD13 */ { 1, 0, 0, 1, 0, 0 }, /* MPULED7 */ | |
186 | /* PD12 */ { 1, 0, 0, 1, 0, 0 }, /* MPULED6 */ | |
187 | /* PD11 */ { 1, 0, 0, 1, 0, 0 }, /* MPULED5 */ | |
188 | /* PD10 */ { 1, 0, 0, 1, 0, 0 }, /* MPULED4 */ | |
189 | /* PD9 */ { 1, 1, 0, 1, 0, 0 }, /* RS232_TXD */ | |
190 | /* PD8 */ { 1, 1, 0, 0, 0, 0 }, /* RD232_RXD */ | |
191 | /* PD7 */ { 1, 0, 0, 0, 0, 0 }, /* not used */ | |
192 | /* PD6 */ { 1, 0, 0, 0, 0, 0 }, /* not used */ | |
193 | /* PD5 */ { 1, 0, 0, 0, 0, 0 }, /* not used */ | |
194 | /* PD4 */ { 1, 0, 0, 0, 0, 0 }, /* not used */ | |
195 | /* PD3 */ { 0, 0, 0, 0, 0, 0 }, /* pin doesn't exist */ | |
196 | /* PD2 */ { 0, 0, 0, 0, 0, 0 }, /* pin doesn't exist */ | |
197 | /* PD1 */ { 0, 0, 0, 0, 0, 0 }, /* pin doesn't exist */ | |
198 | /* PD0 */ { 0, 0, 0, 0, 0, 0 } /* pin doesn't exist */ | |
199 | } | |
200 | }; | |
201 | ||
202 | /*********************************************************************/ | |
203 | /* NAME: checkboard() - Displays the board type and serial number */ | |
204 | /* */ | |
205 | /* OUTPUTS: */ | |
206 | /* Displays the board type and serial number */ | |
207 | /* */ | |
208 | /* RETURNS: */ | |
209 | /* Always returns 1 */ | |
210 | /* */ | |
211 | /* RESTRICTIONS/LIMITATIONS: */ | |
212 | /* */ | |
213 | /* */ | |
214 | /*********************************************************************/ | |
bf9e3b38 | 215 | int checkboard (void) |
afd7f3d0 | 216 | { |
bf9e3b38 | 217 | char *str; |
afd7f3d0 | 218 | |
bf9e3b38 WD |
219 | puts ("Board: Advent Networks gw8260\n"); |
220 | ||
221 | str = getenv ("serial#"); | |
222 | if (str != NULL) { | |
223 | printf ("SN: %s\n", str); | |
224 | } | |
225 | return 0; | |
afd7f3d0 WD |
226 | } |
227 | ||
228 | ||
6d0f6bcf | 229 | #if defined (CONFIG_SYS_DRAM_TEST) |
afd7f3d0 WD |
230 | /*********************************************************************/ |
231 | /* NAME: move64() - moves a double word (64-bit) */ | |
232 | /* */ | |
233 | /* DESCRIPTION: */ | |
234 | /* this function performs a double word move from the data at */ | |
235 | /* the source pointer to the location at the destination pointer. */ | |
236 | /* */ | |
237 | /* INPUTS: */ | |
238 | /* unsigned long long *src - pointer to data to move */ | |
239 | /* */ | |
240 | /* OUTPUTS: */ | |
241 | /* unsigned long long *dest - pointer to locate to move data */ | |
242 | /* */ | |
243 | /* RETURNS: */ | |
244 | /* None */ | |
245 | /* */ | |
246 | /* RESTRICTIONS/LIMITATIONS: */ | |
247 | /* May cloober fr0. */ | |
248 | /* */ | |
249 | /*********************************************************************/ | |
bf9e3b38 | 250 | static void move64 (unsigned long long *src, unsigned long long *dest) |
afd7f3d0 | 251 | { |
bf9e3b38 WD |
252 | asm ("lfd 0, 0(3)\n\t" /* fpr0 = *scr */ |
253 | "stfd 0, 0(4)" /* *dest = fpr0 */ | |
254 | : : : "fr0"); /* Clobbers fr0 */ | |
255 | return; | |
afd7f3d0 WD |
256 | } |
257 | ||
258 | ||
6d0f6bcf | 259 | #if defined (CONFIG_SYS_DRAM_TEST_DATA) |
afd7f3d0 | 260 | |
bf9e3b38 | 261 | unsigned long long pattern[] = { |
eedcd078 WD |
262 | 0xaaaaaaaaaaaaaaaaULL, |
263 | 0xccccccccccccccccULL, | |
264 | 0xf0f0f0f0f0f0f0f0ULL, | |
265 | 0xff00ff00ff00ff00ULL, | |
266 | 0xffff0000ffff0000ULL, | |
267 | 0xffffffff00000000ULL, | |
268 | 0x00000000ffffffffULL, | |
269 | 0x0000ffff0000ffffULL, | |
270 | 0x00ff00ff00ff00ffULL, | |
271 | 0x0f0f0f0f0f0f0f0fULL, | |
272 | 0x3333333333333333ULL, | |
273 | 0x5555555555555555ULL, | |
bf9e3b38 | 274 | }; |
afd7f3d0 WD |
275 | |
276 | /*********************************************************************/ | |
277 | /* NAME: mem_test_data() - test data lines for shorts and opens */ | |
278 | /* */ | |
279 | /* DESCRIPTION: */ | |
280 | /* Tests data lines for shorts and opens by forcing adjacent data */ | |
281 | /* to opposite states. Because the data lines could be routed in */ | |
282 | /* an arbitrary manner the must ensure test patterns ensure that */ | |
283 | /* every case is tested. By using the following series of binary */ | |
284 | /* patterns every combination of adjacent bits is test regardless */ | |
285 | /* of routing. */ | |
286 | /* */ | |
287 | /* ...101010101010101010101010 */ | |
288 | /* ...110011001100110011001100 */ | |
289 | /* ...111100001111000011110000 */ | |
290 | /* ...111111110000000011111111 */ | |
291 | /* */ | |
292 | /* Carrying this out, gives us six hex patterns as follows: */ | |
293 | /* */ | |
294 | /* 0xaaaaaaaaaaaaaaaa */ | |
295 | /* 0xcccccccccccccccc */ | |
296 | /* 0xf0f0f0f0f0f0f0f0 */ | |
297 | /* 0xff00ff00ff00ff00 */ | |
298 | /* 0xffff0000ffff0000 */ | |
299 | /* 0xffffffff00000000 */ | |
300 | /* */ | |
301 | /* The number test patterns will always be given by: */ | |
302 | /* */ | |
303 | /* log(base 2)(number data bits) = log2 (64) = 6 */ | |
304 | /* */ | |
305 | /* To test for short and opens to other signals on our boards. we */ | |
306 | /* simply */ | |
307 | /* test with the 1's complemnt of the paterns as well. */ | |
308 | /* */ | |
309 | /* OUTPUTS: */ | |
310 | /* Displays failing test pattern */ | |
311 | /* */ | |
312 | /* RETURNS: */ | |
313 | /* 0 - Passed test */ | |
314 | /* 1 - Failed test */ | |
315 | /* */ | |
316 | /* RESTRICTIONS/LIMITATIONS: */ | |
317 | /* Assumes only one one SDRAM bank */ | |
318 | /* */ | |
319 | /*********************************************************************/ | |
bf9e3b38 | 320 | int mem_test_data (void) |
afd7f3d0 | 321 | { |
6d0f6bcf | 322 | unsigned long long *pmem = (unsigned long long *) CONFIG_SYS_SDRAM_BASE; |
77ddac94 | 323 | unsigned long long temp64 = 0; |
bf9e3b38 WD |
324 | int num_patterns = sizeof (pattern) / sizeof (pattern[0]); |
325 | int i; | |
326 | unsigned int hi, lo; | |
327 | ||
328 | for (i = 0; i < num_patterns; i++) { | |
329 | move64 (&(pattern[i]), pmem); | |
330 | move64 (pmem, &temp64); | |
331 | ||
332 | /* hi = (temp64>>32) & 0xffffffff; */ | |
333 | /* lo = temp64 & 0xffffffff; */ | |
334 | /* printf("\ntemp64 = 0x%08x%08x", hi, lo); */ | |
335 | ||
336 | hi = (pattern[i] >> 32) & 0xffffffff; | |
337 | lo = pattern[i] & 0xffffffff; | |
338 | /* printf("\npattern[%d] = 0x%08x%08x", i, hi, lo); */ | |
339 | ||
340 | if (temp64 != pattern[i]) { | |
341 | printf ("\n Data Test Failed, pattern 0x%08x%08x", | |
342 | hi, lo); | |
343 | return 1; | |
344 | } | |
afd7f3d0 | 345 | } |
afd7f3d0 | 346 | |
bf9e3b38 | 347 | return 0; |
afd7f3d0 | 348 | } |
6d0f6bcf | 349 | #endif /* CONFIG_SYS_DRAM_TEST_DATA */ |
afd7f3d0 | 350 | |
6d0f6bcf | 351 | #if defined (CONFIG_SYS_DRAM_TEST_ADDRESS) |
afd7f3d0 WD |
352 | /*********************************************************************/ |
353 | /* NAME: mem_test_address() - test address lines */ | |
354 | /* */ | |
355 | /* DESCRIPTION: */ | |
356 | /* This function performs a test to verify that each word im */ | |
357 | /* memory is uniquly addressable. The test sequence is as follows: */ | |
358 | /* */ | |
359 | /* 1) write the address of each word to each word. */ | |
360 | /* 2) verify that each location equals its address */ | |
361 | /* */ | |
362 | /* OUTPUTS: */ | |
363 | /* Displays failing test pattern and address */ | |
364 | /* */ | |
365 | /* RETURNS: */ | |
366 | /* 0 - Passed test */ | |
367 | /* 1 - Failed test */ | |
368 | /* */ | |
369 | /* RESTRICTIONS/LIMITATIONS: */ | |
370 | /* */ | |
371 | /* */ | |
372 | /*********************************************************************/ | |
bf9e3b38 | 373 | int mem_test_address (void) |
afd7f3d0 | 374 | { |
bf9e3b38 | 375 | volatile unsigned int *pmem = |
6d0f6bcf JCPV |
376 | (volatile unsigned int *) CONFIG_SYS_SDRAM_BASE; |
377 | const unsigned int size = (CONFIG_SYS_SDRAM_SIZE * 1024 * 1024) / 4; | |
bf9e3b38 WD |
378 | unsigned int i; |
379 | ||
380 | /* write address to each location */ | |
381 | for (i = 0; i < size; i++) { | |
382 | pmem[i] = i; | |
383 | } | |
afd7f3d0 | 384 | |
bf9e3b38 WD |
385 | /* verify each loaction */ |
386 | for (i = 0; i < size; i++) { | |
387 | if (pmem[i] != i) { | |
388 | printf ("\n Address Test Failed at 0x%x", i); | |
389 | return 1; | |
390 | } | |
afd7f3d0 | 391 | } |
bf9e3b38 | 392 | return 0; |
afd7f3d0 | 393 | } |
6d0f6bcf | 394 | #endif /* CONFIG_SYS_DRAM_TEST_ADDRESS */ |
afd7f3d0 | 395 | |
6d0f6bcf | 396 | #if defined (CONFIG_SYS_DRAM_TEST_WALK) |
afd7f3d0 WD |
397 | /*********************************************************************/ |
398 | /* NAME: mem_march() - memory march */ | |
399 | /* */ | |
400 | /* DESCRIPTION: */ | |
401 | /* Marches up through memory. At each location verifies rmask if */ | |
402 | /* read = 1. At each location write wmask if write = 1. Displays */ | |
403 | /* failing address and pattern. */ | |
404 | /* */ | |
405 | /* INPUTS: */ | |
406 | /* volatile unsigned long long * base - start address of test */ | |
407 | /* unsigned int size - number of dwords(64-bit) to test */ | |
408 | /* unsigned long long rmask - read verify mask */ | |
409 | /* unsigned long long wmask - wrtie verify mask */ | |
410 | /* short read - verifies rmask if read = 1 */ | |
411 | /* short write - writes wmask if write = 1 */ | |
412 | /* */ | |
413 | /* OUTPUTS: */ | |
414 | /* Displays failing test pattern and address */ | |
415 | /* */ | |
416 | /* RETURNS: */ | |
417 | /* 0 - Passed test */ | |
418 | /* 1 - Failed test */ | |
419 | /* */ | |
420 | /* RESTRICTIONS/LIMITATIONS: */ | |
421 | /* */ | |
422 | /* */ | |
423 | /*********************************************************************/ | |
bf9e3b38 WD |
424 | int mem_march (volatile unsigned long long *base, |
425 | unsigned int size, | |
426 | unsigned long long rmask, | |
427 | unsigned long long wmask, short read, short write) | |
afd7f3d0 | 428 | { |
bf9e3b38 | 429 | unsigned int i; |
77ddac94 | 430 | unsigned long long temp = 0; |
bf9e3b38 WD |
431 | unsigned int hitemp, lotemp, himask, lomask; |
432 | ||
433 | for (i = 0; i < size; i++) { | |
434 | if (read != 0) { | |
435 | /* temp = base[i]; */ | |
436 | move64 ((unsigned long long *) &(base[i]), &temp); | |
437 | if (rmask != temp) { | |
438 | hitemp = (temp >> 32) & 0xffffffff; | |
439 | lotemp = temp & 0xffffffff; | |
440 | himask = (rmask >> 32) & 0xffffffff; | |
441 | lomask = rmask & 0xffffffff; | |
442 | ||
443 | printf ("\n Walking one's test failed: address = 0x%08x," "\n\texpected 0x%08x%08x, found 0x%08x%08x", i << 3, himask, lomask, hitemp, lotemp); | |
444 | return 1; | |
445 | } | |
446 | } | |
447 | if (write != 0) { | |
448 | /* base[i] = wmask; */ | |
449 | move64 (&wmask, (unsigned long long *) &(base[i])); | |
450 | } | |
afd7f3d0 | 451 | } |
bf9e3b38 | 452 | return 0; |
afd7f3d0 | 453 | } |
6d0f6bcf | 454 | #endif /* CONFIG_SYS_DRAM_TEST_WALK */ |
afd7f3d0 WD |
455 | |
456 | /*********************************************************************/ | |
457 | /* NAME: mem_test_walk() - a simple walking ones test */ | |
458 | /* */ | |
459 | /* DESCRIPTION: */ | |
460 | /* Performs a walking ones through entire physical memory. The */ | |
461 | /* test uses as series of memory marches, mem_march(), to verify */ | |
462 | /* and write the test patterns to memory. The test sequence is as */ | |
463 | /* follows: */ | |
464 | /* 1) march writing 0000...0001 */ | |
465 | /* 2) march verifying 0000...0001 , writing 0000...0010 */ | |
466 | /* 3) repeat step 2 shifting masks left 1 bit each time unitl */ | |
467 | /* the write mask equals 1000...0000 */ | |
468 | /* 4) march verifying 1000...0000 */ | |
469 | /* The test fails if any of the memory marches return a failure. */ | |
470 | /* */ | |
471 | /* OUTPUTS: */ | |
472 | /* Displays which pass on the memory test is executing */ | |
473 | /* */ | |
474 | /* RETURNS: */ | |
475 | /* 0 - Passed test */ | |
476 | /* 1 - Failed test */ | |
477 | /* */ | |
478 | /* RESTRICTIONS/LIMITATIONS: */ | |
479 | /* */ | |
480 | /* */ | |
481 | /*********************************************************************/ | |
bf9e3b38 | 482 | int mem_test_walk (void) |
afd7f3d0 | 483 | { |
bf9e3b38 WD |
484 | unsigned long long mask; |
485 | volatile unsigned long long *pmem = | |
6d0f6bcf JCPV |
486 | (volatile unsigned long long *) CONFIG_SYS_SDRAM_BASE; |
487 | const unsigned long size = (CONFIG_SYS_SDRAM_SIZE * 1024 * 1024) / 8; | |
bf9e3b38 WD |
488 | |
489 | unsigned int i; | |
490 | ||
491 | mask = 0x01; | |
492 | ||
493 | printf ("Initial Pass"); | |
494 | mem_march (pmem, size, 0x0, 0x1, 0, 1); | |
495 | ||
496 | printf ("\b\b\b\b\b\b\b\b\b\b\b\b"); | |
497 | printf (" "); | |
498 | printf ("\b\b\b\b\b\b\b\b\b\b\b\b"); | |
499 | ||
500 | for (i = 0; i < 63; i++) { | |
501 | printf ("Pass %2d", i + 2); | |
502 | if (mem_march (pmem, size, mask, mask << 1, 1, 1) != 0) { | |
503 | /*printf("mask: 0x%x, pass: %d, ", mask, i); */ | |
504 | return 1; | |
505 | } | |
506 | mask = mask << 1; | |
507 | printf ("\b\b\b\b\b\b\b"); | |
afd7f3d0 | 508 | } |
afd7f3d0 | 509 | |
bf9e3b38 WD |
510 | printf ("Last Pass"); |
511 | if (mem_march (pmem, size, 0, mask, 0, 1) != 0) { | |
512 | /* printf("mask: 0x%x", mask); */ | |
513 | return 1; | |
514 | } | |
515 | printf ("\b\b\b\b\b\b\b\b\b"); | |
516 | printf (" "); | |
517 | printf ("\b\b\b\b\b\b\b\b\b"); | |
afd7f3d0 | 518 | |
bf9e3b38 | 519 | return 0; |
afd7f3d0 WD |
520 | } |
521 | ||
522 | /*********************************************************************/ | |
523 | /* NAME: testdram() - calls any enabled memory tests */ | |
524 | /* */ | |
525 | /* DESCRIPTION: */ | |
526 | /* Runs memory tests if the environment test variables are set to */ | |
527 | /* 'y'. */ | |
528 | /* */ | |
529 | /* INPUTS: */ | |
530 | /* testdramdata - If set to 'y', data test is run. */ | |
531 | /* testdramaddress - If set to 'y', address test is run. */ | |
532 | /* testdramwalk - If set to 'y', walking ones test is run */ | |
533 | /* */ | |
534 | /* OUTPUTS: */ | |
535 | /* None */ | |
536 | /* */ | |
537 | /* RETURNS: */ | |
538 | /* 0 - Passed test */ | |
539 | /* 1 - Failed test */ | |
540 | /* */ | |
541 | /* RESTRICTIONS/LIMITATIONS: */ | |
542 | /* */ | |
543 | /* */ | |
544 | /*********************************************************************/ | |
bf9e3b38 | 545 | int testdram (void) |
afd7f3d0 | 546 | { |
bf9e3b38 WD |
547 | char *s; |
548 | int rundata, runaddress, runwalk; | |
549 | ||
550 | s = getenv ("testdramdata"); | |
551 | rundata = (s && (*s == 'y')) ? 1 : 0; | |
552 | s = getenv ("testdramaddress"); | |
553 | runaddress = (s && (*s == 'y')) ? 1 : 0; | |
554 | s = getenv ("testdramwalk"); | |
555 | runwalk = (s && (*s == 'y')) ? 1 : 0; | |
556 | ||
557 | if ((rundata == 1) || (runaddress == 1) || (runwalk == 1)) { | |
558 | printf ("Testing RAM ... "); | |
559 | } | |
6d0f6bcf | 560 | #ifdef CONFIG_SYS_DRAM_TEST_DATA |
bf9e3b38 WD |
561 | if (rundata == 1) { |
562 | if (mem_test_data () == 1) { | |
563 | return 1; | |
564 | } | |
afd7f3d0 | 565 | } |
afd7f3d0 | 566 | #endif |
6d0f6bcf | 567 | #ifdef CONFIG_SYS_DRAM_TEST_ADDRESS |
bf9e3b38 WD |
568 | if (runaddress == 1) { |
569 | if (mem_test_address () == 1) { | |
570 | return 1; | |
571 | } | |
afd7f3d0 | 572 | } |
afd7f3d0 | 573 | #endif |
6d0f6bcf | 574 | #ifdef CONFIG_SYS_DRAM_TEST_WALK |
bf9e3b38 WD |
575 | if (runwalk == 1) { |
576 | if (mem_test_walk () == 1) { | |
577 | return 1; | |
578 | } | |
afd7f3d0 | 579 | } |
afd7f3d0 | 580 | #endif |
bf9e3b38 WD |
581 | if ((rundata == 1) || (runaddress == 1) || (runwalk == 1)) { |
582 | printf ("passed"); | |
583 | } | |
584 | return 0; | |
afd7f3d0 WD |
585 | |
586 | } | |
6d0f6bcf | 587 | #endif /* CONFIG_SYS_DRAM_TEST */ |
afd7f3d0 WD |
588 | |
589 | /*********************************************************************/ | |
590 | /* NAME: initdram() - initializes SDRAM controller */ | |
591 | /* */ | |
592 | /* DESCRIPTION: */ | |
593 | /* Initializes the MPC8260's SDRAM controller. */ | |
594 | /* */ | |
595 | /* INPUTS: */ | |
6d0f6bcf JCPV |
596 | /* CONFIG_SYS_IMMR - MPC8260 Internal memory map */ |
597 | /* CONFIG_SYS_SDRAM_BASE - Physical start address of SDRAM */ | |
598 | /* CONFIG_SYS_PSDMR - SDRAM mode register */ | |
599 | /* CONFIG_SYS_MPTPR - Memory refresh timer prescaler register */ | |
600 | /* CONFIG_SYS_SDRAM0_SIZE - SDRAM size */ | |
afd7f3d0 WD |
601 | /* */ |
602 | /* RETURNS: */ | |
603 | /* SDRAM size in bytes */ | |
604 | /* */ | |
605 | /* RESTRICTIONS/LIMITATIONS: */ | |
606 | /* */ | |
607 | /* */ | |
608 | /*********************************************************************/ | |
9973e3c6 | 609 | phys_size_t initdram (int board_type) |
afd7f3d0 | 610 | { |
6d0f6bcf | 611 | volatile immap_t *immap = (immap_t *) CONFIG_SYS_IMMR; |
bf9e3b38 | 612 | volatile memctl8260_t *memctl = &immap->im_memctl; |
6d0f6bcf JCPV |
613 | volatile uchar c = 0, *ramaddr = (uchar *) (CONFIG_SYS_SDRAM_BASE + 0x8); |
614 | ulong psdmr = CONFIG_SYS_PSDMR; | |
bf9e3b38 WD |
615 | int i; |
616 | ||
617 | /* | |
618 | * Quote from 8260 UM (10.4.2 SDRAM Power-On Initialization, 10-35): | |
619 | * | |
620 | * "At system reset, initialization software must set up the | |
621 | * programmable parameters in the memory controller banks registers | |
622 | * (ORx, BRx, P/LSDMR). After all memory parameters are configured, | |
623 | * system software should execute the following initialization sequence | |
624 | * for each SDRAM device. | |
625 | * | |
626 | * 1. Issue a PRECHARGE-ALL-BANKS command | |
627 | * 2. Issue eight CBR REFRESH commands | |
628 | * 3. Issue a MODE-SET command to initialize the mode register | |
629 | * | |
630 | * The initial commands are executed by setting P/LSDMR[OP] and | |
631 | * accessing the SDRAM with a single-byte transaction." | |
632 | * | |
633 | * The appropriate BRx/ORx registers have already been set when we | |
6d0f6bcf | 634 | * get here. The SDRAM can be accessed at the address CONFIG_SYS_SDRAM_BASE. |
bf9e3b38 WD |
635 | */ |
636 | ||
6d0f6bcf JCPV |
637 | memctl->memc_psrt = CONFIG_SYS_PSRT; |
638 | memctl->memc_mptpr = CONFIG_SYS_MPTPR; | |
bf9e3b38 WD |
639 | |
640 | memctl->memc_psdmr = psdmr | PSDMR_OP_PREA; | |
afd7f3d0 | 641 | *ramaddr = c; |
afd7f3d0 | 642 | |
bf9e3b38 WD |
643 | memctl->memc_psdmr = psdmr | PSDMR_OP_CBRR; |
644 | for (i = 0; i < 8; i++) { | |
645 | *ramaddr = c; | |
646 | } | |
647 | memctl->memc_psdmr = psdmr | PSDMR_OP_MRW; | |
648 | *ramaddr = c; | |
649 | ||
650 | memctl->memc_psdmr = psdmr | PSDMR_OP_NORM | PSDMR_RFEN; | |
651 | *ramaddr = c; | |
afd7f3d0 | 652 | |
bf9e3b38 | 653 | /* return total ram size */ |
6d0f6bcf | 654 | return (CONFIG_SYS_SDRAM0_SIZE * 1024 * 1024); |
afd7f3d0 WD |
655 | } |
656 | ||
657 | /*********************************************************************/ | |
658 | /* End of gw8260.c */ | |
659 | /*********************************************************************/ |