]> git.ipfire.org Git - people/ms/u-boot.git/blob - board/ocotea/flash.c
bc0d2c9c164e4c8b3d0cfca3c26adb268488ecf2
[people/ms/u-boot.git] / board / ocotea / flash.c
1 /*
2 * (C) Copyright 2004-2005
3 * Wolfgang Denk, DENX Software Engineering, wd@denx.de.
4 *
5 * (C) Copyright 2002 Jun Gu <jung@artesyncp.com>
6 * Add support for Am29F016D and dynamic switch setting.
7 *
8 * See file CREDITS for list of people who contributed to this
9 * project.
10 *
11 * This program is free software; you can redistribute it and/or
12 * modify it under the terms of the GNU General Public License as
13 * published by the Free Software Foundation; either version 2 of
14 * the License, or (at your option) any later version.
15 *
16 * This program is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 * GNU General Public License for more details.
20 *
21 * You should have received a copy of the GNU General Public License
22 * along with this program; if not, write to the Free Software
23 * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
24 * MA 02111-1307 USA
25 */
26
27 /*
28 * Modified 4/5/2001
29 * Wait for completion of each sector erase command issued
30 * 4/5/2001
31 * Chris Hallinan - DS4.COM, Inc. - clh@net1plus.com
32 */
33
34 #include <common.h>
35 #include <ppc4xx.h>
36 #include <asm/processor.h>
37
38 #undef DEBUG
39
40 #ifdef DEBUG
41 #define DEBUGF(x...) printf(x)
42 #else
43 #define DEBUGF(x...)
44 #endif /* DEBUG */
45
46 #define BOOT_SMALL_FLASH 0x40 /* 01000000 */
47 #define FLASH_ONBD_N 2 /* 00000010 */
48 #define FLASH_SRAM_SEL 1 /* 00000001 */
49 #define FLASH_ONBD_N 2 /* 00000010 */
50 #define FLASH_SRAM_SEL 1 /* 00000001 */
51
52 #define BOOT_SMALL_FLASH_VAL 4
53 #define FLASH_ONBD_N_VAL 2
54 #define FLASH_SRAM_SEL_VAL 1
55
56
57 flash_info_t flash_info[CFG_MAX_FLASH_BANKS]; /* info for FLASH chips */
58
59 static unsigned long flash_addr_table[8][CFG_MAX_FLASH_BANKS] = {
60 {0xFF800000, 0xFF880000, 0xFFC00000}, /* 0:000: configuraton 4 */
61 {0xFF900000, 0xFF980000, 0xFFC00000}, /* 1:001: configuraton 3 */
62 {0x00000000, 0x00000000, 0x00000000}, /* 2:010: configuraton 8 */
63 {0x00000000, 0x00000000, 0x00000000}, /* 3:011: configuraton 7 */
64 {0xFFE00000, 0xFFF00000, 0xFF800000}, /* 4:100: configuraton 2 */
65 {0xFFF00000, 0xFFF80000, 0xFF800000}, /* 5:101: configuraton 1 */
66 {0x00000000, 0x00000000, 0x00000000}, /* 6:110: configuraton 6 */
67 {0x00000000, 0x00000000, 0x00000000} /* 7:111: configuraton 5 */
68 };
69
70 /*-----------------------------------------------------------------------
71 * Functions
72 */
73 static ulong flash_get_size(vu_long * addr, flash_info_t * info);
74 static int write_word(flash_info_t * info, ulong dest, ulong data);
75
76
77 #ifdef CONFIG_OCOTEA
78 #define ADDR0 0x5555
79 #define ADDR1 0x2aaa
80 #define FLASH_WORD_SIZE unsigned char
81 #endif
82
83 /*-----------------------------------------------------------------------
84 */
85
86 unsigned long flash_init(void)
87 {
88 unsigned long total_b = 0;
89 unsigned long size_b[CFG_MAX_FLASH_BANKS];
90 unsigned char *fpga_base = (unsigned char *) CFG_FPGA_BASE;
91 unsigned char switch_status;
92 unsigned short index = 0;
93 int i;
94
95 /* read FPGA base register FPGA_REG0 */
96 switch_status = *fpga_base;
97
98 /* check the bitmap of switch status */
99 if (switch_status & BOOT_SMALL_FLASH) {
100 index += BOOT_SMALL_FLASH_VAL;
101 }
102 if (switch_status & FLASH_ONBD_N) {
103 index += FLASH_ONBD_N_VAL;
104 }
105 if (switch_status & FLASH_SRAM_SEL) {
106 index += FLASH_SRAM_SEL_VAL;
107 }
108
109 DEBUGF("\n");
110 DEBUGF("FLASH: Index: %d\n", index);
111
112 /* Init: no FLASHes known */
113 for (i = 0; i < CFG_MAX_FLASH_BANKS; ++i) {
114 flash_info[i].flash_id = FLASH_UNKNOWN;
115 flash_info[i].sector_count = -1;
116 flash_info[i].size = 0;
117
118 /* check whether the address is 0 */
119 if (flash_addr_table[index][i] == 0) {
120 continue;
121 }
122
123 /* call flash_get_size() to initialize sector address */
124 size_b[i] = flash_get_size((vu_long *) flash_addr_table[index][i], &flash_info[i]);
125 flash_info[i].size = size_b[i];
126 if (flash_info[i].flash_id == FLASH_UNKNOWN) {
127 printf ("## Unknown FLASH on Bank %d - Size = 0x%08lx = %ld MB\n",
128 i, size_b[i], size_b[i] << 20);
129 flash_info[i].sector_count = -1;
130 flash_info[i].size = 0;
131 }
132
133 total_b += flash_info[i].size;
134 }
135
136 /* Monitor protection ON by default */
137 (void)flash_protect(FLAG_PROTECT_SET,
138 -CFG_MONITOR_LEN,
139 0xffffffff,
140 &flash_info[2]);
141
142 return total_b;
143 }
144
145 /*-----------------------------------------------------------------------
146 */
147 void flash_print_info(flash_info_t * info)
148 {
149 int i;
150 int k;
151 int size;
152 int erased;
153 volatile unsigned long *flash;
154
155 if (info->flash_id == FLASH_UNKNOWN) {
156 printf("missing or unknown FLASH type\n");
157 return;
158 }
159
160 switch (info->flash_id & FLASH_VENDMASK) {
161 case FLASH_MAN_AMD:
162 printf("AMD ");
163 break;
164 case FLASH_MAN_STM:
165 printf("STM ");
166 break;
167 case FLASH_MAN_FUJ:
168 printf("FUJITSU ");
169 break;
170 case FLASH_MAN_SST:
171 printf("SST ");
172 break;
173 default:
174 printf("Unknown Vendor ");
175 break;
176 }
177
178 switch (info->flash_id & FLASH_TYPEMASK) {
179 case FLASH_AM040:
180 printf("AM29F040 (512 Kbit, uniform sector size)\n");
181 break;
182 case FLASH_AM400B:
183 printf("AM29LV400B (4 Mbit, bottom boot sect)\n");
184 break;
185 case FLASH_AM400T:
186 printf("AM29LV400T (4 Mbit, top boot sector)\n");
187 break;
188 case FLASH_AM800B:
189 printf("AM29LV800B (8 Mbit, bottom boot sect)\n");
190 break;
191 case FLASH_AM800T:
192 printf("AM29LV800T (8 Mbit, top boot sector)\n");
193 break;
194 case FLASH_AM160B:
195 printf("AM29LV160B (16 Mbit, bottom boot sect)\n");
196 break;
197 case FLASH_AM160T:
198 printf("AM29LV160T (16 Mbit, top boot sector)\n");
199 break;
200 case FLASH_AM320B:
201 printf("AM29LV320B (32 Mbit, bottom boot sect)\n");
202 break;
203 case FLASH_AM320T:
204 printf("AM29LV320T (32 Mbit, top boot sector)\n");
205 break;
206 case FLASH_AMDLV033C:
207 printf("AM29LV033C (32 Mbit, top boot sector)\n");
208 break;
209 case FLASH_SST800A:
210 printf("SST39LF/VF800 (8 Mbit, uniform sector size)\n");
211 break;
212 case FLASH_SST160A:
213 printf("SST39LF/VF160 (16 Mbit, uniform sector size)\n");
214 break;
215 default:
216 printf("Unknown Chip Type\n");
217 break;
218 }
219
220 printf(" Size: %ld KB in %d Sectors\n",
221 info->size >> 10, info->sector_count);
222
223 printf(" Sector Start Addresses:");
224 for (i = 0; i < info->sector_count; ++i) {
225 /*
226 * Check if whole sector is erased
227 */
228 if (i != (info->sector_count - 1))
229 size = info->start[i + 1] - info->start[i];
230 else
231 size = info->start[0] + info->size - info->start[i];
232 erased = 1;
233 flash = (volatile unsigned long *) info->start[i];
234 size = size >> 2; /* divide by 4 for longword access */
235 for (k = 0; k < size; k++) {
236 if (*flash++ != 0xffffffff) {
237 erased = 0;
238 break;
239 }
240 }
241
242 if ((i % 5) == 0)
243 printf("\n ");
244 printf(" %08lX%s%s",
245 info->start[i],
246 erased ? " E" : " ", info->protect[i] ? "RO " : " ");
247 }
248 printf("\n");
249 return;
250 }
251
252 /*-----------------------------------------------------------------------
253 */
254
255 /*
256 * The following code cannot be run from FLASH!
257 */
258 static ulong flash_get_size(vu_long * addr, flash_info_t * info)
259 {
260 short i;
261 FLASH_WORD_SIZE value;
262 ulong base = (ulong) addr;
263 volatile FLASH_WORD_SIZE *addr2 = (FLASH_WORD_SIZE *) addr;
264
265 DEBUGF("FLASH ADDR: %08x\n", (unsigned) addr);
266
267 /* Write auto select command: read Manufacturer ID */
268 udelay(10000);
269 addr2[ADDR0] = (FLASH_WORD_SIZE) 0x00AA00AA;
270 udelay(1000);
271 addr2[ADDR1] = (FLASH_WORD_SIZE) 0x00550055;
272 udelay(1000);
273 addr2[ADDR0] = (FLASH_WORD_SIZE) 0x00900090;
274 udelay(1000);
275
276 value = addr2[0];
277 DEBUGF("FLASH MANUFACT: %x\n", value);
278
279 switch (value) {
280 case (FLASH_WORD_SIZE) AMD_MANUFACT:
281 info->flash_id = FLASH_MAN_AMD;
282 break;
283 case (FLASH_WORD_SIZE) FUJ_MANUFACT:
284 info->flash_id = FLASH_MAN_FUJ;
285 break;
286 case (FLASH_WORD_SIZE) SST_MANUFACT:
287 info->flash_id = FLASH_MAN_SST;
288 break;
289 case (FLASH_WORD_SIZE) STM_MANUFACT:
290 info->flash_id = FLASH_MAN_STM;
291 break;
292 default:
293 info->flash_id = FLASH_UNKNOWN;
294 info->sector_count = 0;
295 info->size = 0;
296 return (0); /* no or unknown flash */
297 }
298
299 value = addr2[1]; /* device ID */
300
301 DEBUGF("\nFLASH DEVICEID: %x\n", value);
302
303 switch (value) {
304 case (FLASH_WORD_SIZE) AMD_ID_LV040B:
305 info->flash_id += FLASH_AM040;
306 info->sector_count = 8;
307 info->size = 0x0080000; /* => 512 ko */
308 break;
309 case (FLASH_WORD_SIZE) AMD_ID_F040B:
310 info->flash_id += FLASH_AM040;
311 info->sector_count = 8;
312 info->size = 0x0080000; /* => 512 ko */
313 break;
314 case (FLASH_WORD_SIZE) STM_ID_M29W040B:
315 info->flash_id += FLASH_AM040;
316 info->sector_count = 8;
317 info->size = 0x0080000; /* => 512 ko */
318 break;
319 case (FLASH_WORD_SIZE) AMD_ID_LV033C:
320 info->flash_id += FLASH_AMDLV033C;
321 info->sector_count = 64;
322 info->size = 0x00400000;
323 break; /* => 4 MB */
324 default:
325 info->flash_id = FLASH_UNKNOWN;
326 return (0); /* => no or unknown flash */
327 }
328
329 /* set up sector start address table */
330 if (((info->flash_id & FLASH_VENDMASK) == FLASH_MAN_SST) ||
331 ((info->flash_id & FLASH_TYPEMASK) == FLASH_AM040) ||
332 ((info->flash_id & FLASH_TYPEMASK) == FLASH_AMD016)) {
333 for (i = 0; i < info->sector_count; i++)
334 info->start[i] = base + (i * 0x00010000);
335 } else {
336 if (info->flash_id & FLASH_BTYPE) {
337 /* set sector offsets for bottom boot block type */
338 info->start[0] = base + 0x00000000;
339 info->start[1] = base + 0x00004000;
340 info->start[2] = base + 0x00006000;
341 info->start[3] = base + 0x00008000;
342 for (i = 4; i < info->sector_count; i++) {
343 info->start[i] = base + (i * 0x00010000) - 0x00030000;
344 }
345 } else {
346 /* set sector offsets for top boot block type */
347 i = info->sector_count - 1;
348 info->start[i--] = base + info->size - 0x00004000;
349 info->start[i--] = base + info->size - 0x00006000;
350 info->start[i--] = base + info->size - 0x00008000;
351 for (; i >= 0; i--) {
352 info->start[i] = base + i * 0x00010000;
353 }
354 }
355 }
356
357 /* check for protected sectors */
358 for (i = 0; i < info->sector_count; i++) {
359 /* read sector protection at sector address, (A7 .. A0) = 0x02 */
360 /* D0 = 1 if protected */
361 addr2 = (volatile FLASH_WORD_SIZE *) (info->start[i]);
362
363 /* For AMD29033C flash we need to resend the command of *
364 * reading flash protection for upper 8 Mb of flash */
365 if ( i == 32 ) {
366 addr2[ADDR0] = (FLASH_WORD_SIZE) 0xAAAAAAAA;
367 addr2[ADDR1] = (FLASH_WORD_SIZE) 0x55555555;
368 addr2[ADDR0] = (FLASH_WORD_SIZE) 0x90909090;
369 }
370
371 if ((info->flash_id & FLASH_VENDMASK) == FLASH_MAN_SST)
372 info->protect[i] = 0;
373 else
374 info->protect[i] = addr2[2] & 1;
375 }
376
377 /* issue bank reset to return to read mode */
378 addr2[0] = (FLASH_WORD_SIZE) 0x00F000F0;
379
380 /*
381 * Prevent writes to uninitialized FLASH.
382 */
383 if (info->flash_id != FLASH_UNKNOWN) {
384 /* ? ? ? */
385 }
386
387 return (info->size);
388 }
389
390 int wait_for_DQ7(flash_info_t * info, int sect)
391 {
392 ulong start, now, last;
393 volatile FLASH_WORD_SIZE *addr =
394 (FLASH_WORD_SIZE *) (info->start[sect]);
395
396 start = get_timer(0);
397 last = start;
398 while ((addr[0] & (FLASH_WORD_SIZE) 0x00800080) !=
399 (FLASH_WORD_SIZE) 0x00800080) {
400 if ((now = get_timer(start)) > CFG_FLASH_ERASE_TOUT) {
401 printf("Timeout\n");
402 return -1;
403 }
404 /* show that we're waiting */
405 if ((now - last) > 1000) { /* every second */
406 putc('.');
407 last = now;
408 }
409 }
410 return 0;
411 }
412
413 /*-----------------------------------------------------------------------
414 */
415
416 int flash_erase(flash_info_t * info, int s_first, int s_last)
417 {
418 volatile FLASH_WORD_SIZE *addr = (FLASH_WORD_SIZE *) (info->start[0]);
419 volatile FLASH_WORD_SIZE *addr2;
420 int flag, prot, sect, l_sect;
421 int i;
422
423 if ((s_first < 0) || (s_first > s_last)) {
424 if (info->flash_id == FLASH_UNKNOWN) {
425 printf("- missing\n");
426 } else {
427 printf("- no sectors to erase\n");
428 }
429 return 1;
430 }
431
432 if (info->flash_id == FLASH_UNKNOWN) {
433 printf("Can't erase unknown flash type - aborted\n");
434 return 1;
435 }
436
437 prot = 0;
438 for (sect = s_first; sect <= s_last; ++sect) {
439 if (info->protect[sect]) {
440 prot++;
441 }
442 }
443
444 if (prot) {
445 printf("- Warning: %d protected sectors will not be erased!\n",
446 prot);
447 } else {
448 printf("\n");
449 }
450
451 l_sect = -1;
452
453 /* Disable interrupts which might cause a timeout here */
454 flag = disable_interrupts();
455
456 /* Start erase on unprotected sectors */
457 for (sect = s_first; sect <= s_last; sect++) {
458 if (info->protect[sect] == 0) { /* not protected */
459 addr2 = (FLASH_WORD_SIZE *) (info->start[sect]);
460
461 if ((info->flash_id & FLASH_VENDMASK) == FLASH_MAN_SST) {
462 addr[ADDR0] = (FLASH_WORD_SIZE) 0x00AA00AA;
463 addr[ADDR1] = (FLASH_WORD_SIZE) 0x00550055;
464 addr[ADDR0] = (FLASH_WORD_SIZE) 0x00800080;
465 addr[ADDR0] = (FLASH_WORD_SIZE) 0x00AA00AA;
466 addr[ADDR1] = (FLASH_WORD_SIZE) 0x00550055;
467 addr2[0] = (FLASH_WORD_SIZE) 0x00500050; /* block erase */
468 for (i = 0; i < 50; i++)
469 udelay(1000); /* wait 1 ms */
470 } else {
471 addr[ADDR0] = (FLASH_WORD_SIZE) 0x00AA00AA;
472 addr[ADDR1] = (FLASH_WORD_SIZE) 0x00550055;
473 addr[ADDR0] = (FLASH_WORD_SIZE) 0x00800080;
474 addr[ADDR0] = (FLASH_WORD_SIZE) 0x00AA00AA;
475 addr[ADDR1] = (FLASH_WORD_SIZE) 0x00550055;
476 addr2[0] = (FLASH_WORD_SIZE) 0x00300030; /* sector erase */
477 }
478 l_sect = sect;
479 /*
480 * Wait for each sector to complete, it's more
481 * reliable. According to AMD Spec, you must
482 * issue all erase commands within a specified
483 * timeout. This has been seen to fail, especially
484 * if printf()s are included (for debug)!!
485 */
486 wait_for_DQ7(info, sect);
487 }
488 }
489
490 /* re-enable interrupts if necessary */
491 if (flag)
492 enable_interrupts();
493
494 /* wait at least 80us - let's wait 1 ms */
495 udelay(1000);
496
497 /* reset to read mode */
498 addr = (FLASH_WORD_SIZE *) info->start[0];
499 addr[0] = (FLASH_WORD_SIZE) 0x00F000F0; /* reset bank */
500
501 printf(" done\n");
502 return 0;
503 }
504
505 /*-----------------------------------------------------------------------
506 * Copy memory to flash, returns:
507 * 0 - OK
508 * 1 - write timeout
509 * 2 - Flash not erased
510 */
511 int write_buff(flash_info_t * info, uchar * src, ulong addr, ulong cnt)
512 {
513 ulong cp, wp, data;
514 int i, l, rc;
515
516 wp = (addr & ~3); /* get lower word aligned address */
517
518 /*
519 * handle unaligned start bytes
520 */
521 if ((l = addr - wp) != 0) {
522 data = 0;
523 for (i = 0, cp = wp; i < l; ++i, ++cp) {
524 data = (data << 8) | (*(uchar *) cp);
525 }
526 for (; i < 4 && cnt > 0; ++i) {
527 data = (data << 8) | *src++;
528 --cnt;
529 ++cp;
530 }
531 for (; cnt == 0 && i < 4; ++i, ++cp) {
532 data = (data << 8) | (*(uchar *) cp);
533 }
534
535 if ((rc = write_word(info, wp, data)) != 0) {
536 return (rc);
537 }
538 wp += 4;
539 }
540
541 /*
542 * handle word aligned part
543 */
544 while (cnt >= 4) {
545 data = 0;
546 for (i = 0; i < 4; ++i) {
547 data = (data << 8) | *src++;
548 }
549 if ((rc = write_word(info, wp, data)) != 0) {
550 return (rc);
551 }
552 wp += 4;
553 cnt -= 4;
554 }
555
556 if (cnt == 0) {
557 return (0);
558 }
559
560 /*
561 * handle unaligned tail bytes
562 */
563 data = 0;
564 for (i = 0, cp = wp; i < 4 && cnt > 0; ++i, ++cp) {
565 data = (data << 8) | *src++;
566 --cnt;
567 }
568 for (; i < 4; ++i, ++cp) {
569 data = (data << 8) | (*(uchar *) cp);
570 }
571
572 return (write_word(info, wp, data));
573 }
574
575 /*-----------------------------------------------------------------------
576 * Write a word to Flash, returns:
577 * 0 - OK
578 * 1 - write timeout
579 * 2 - Flash not erased
580 */
581 static int write_word(flash_info_t * info, ulong dest, ulong data)
582 {
583 volatile FLASH_WORD_SIZE *addr2 = (FLASH_WORD_SIZE *) (info->start[0]);
584 volatile FLASH_WORD_SIZE *dest2 = (FLASH_WORD_SIZE *) dest;
585 volatile FLASH_WORD_SIZE *data2 = (FLASH_WORD_SIZE *) & data;
586 ulong start;
587 int i;
588
589 /* Check if Flash is (sufficiently) erased */
590 if ((*((volatile FLASH_WORD_SIZE *) dest) &
591 (FLASH_WORD_SIZE) data) != (FLASH_WORD_SIZE) data) {
592 return (2);
593 }
594
595 for (i = 0; i < 4 / sizeof(FLASH_WORD_SIZE); i++) {
596 int flag;
597
598 /* Disable interrupts which might cause a timeout here */
599 flag = disable_interrupts();
600
601 addr2[ADDR0] = (FLASH_WORD_SIZE) 0x00AA00AA;
602 addr2[ADDR1] = (FLASH_WORD_SIZE) 0x00550055;
603 addr2[ADDR0] = (FLASH_WORD_SIZE) 0x00A000A0;
604
605 dest2[i] = data2[i];
606
607 /* re-enable interrupts if necessary */
608 if (flag)
609 enable_interrupts();
610
611 /* data polling for D7 */
612 start = get_timer(0);
613 while ((dest2[i] & (FLASH_WORD_SIZE) 0x00800080) !=
614 (data2[i] & (FLASH_WORD_SIZE) 0x00800080)) {
615
616 if (get_timer(start) > CFG_FLASH_WRITE_TOUT) {
617 return (1);
618 }
619 }
620 }
621
622 return (0);
623 }