~ubuntu-branches/ubuntu/maverick/u-boot-omap3/maverick

« back to all changes in this revision

Viewing changes to board/snmc/qs860t/flash.c

  • Committer: Bazaar Package Importer
  • Author(s): Oliver Grawert
  • Date: 2010-03-22 15:06:23 UTC
  • Revision ID: james.westby@ubuntu.com-20100322150623-i21g8rgiyl5dohag
Tags: upstream-2010.3git20100315
ImportĀ upstreamĀ versionĀ 2010.3git20100315

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/*
 
2
 * (C) Copyright 2003
 
3
 * MuLogic B.V.
 
4
 *
 
5
 * (C) Copyright 2001
 
6
 * Wolfgang Denk, DENX Software Engineering, wd@denx.de.
 
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
#include <common.h>
 
28
#include <ppc4xx.h>
 
29
#include <asm/u-boot.h>
 
30
#include <asm/processor.h>
 
31
 
 
32
flash_info_t flash_info[CONFIG_SYS_MAX_FLASH_BANKS]; /* info for FLASH chips */
 
33
 
 
34
 
 
35
#ifdef CONFIG_SYS_FLASH_16BIT
 
36
#define FLASH_WORD_SIZE unsigned short
 
37
#define FLASH_ID_MASK   0xFFFF
 
38
#else
 
39
#define FLASH_WORD_SIZE unsigned long
 
40
#define FLASH_ID_MASK   0xFFFFFFFF
 
41
#endif
 
42
 
 
43
/*-----------------------------------------------------------------------
 
44
 * Functions
 
45
 */
 
46
/* stolen from esteem192e/flash.c */
 
47
ulong flash_get_size (volatile FLASH_WORD_SIZE *addr, flash_info_t *info);
 
48
 
 
49
#ifndef CONFIG_SYS_FLASH_16BIT
 
50
static int write_word (flash_info_t *info, ulong dest, ulong data);
 
51
#else
 
52
static int write_short (flash_info_t *info, ulong dest, ushort data);
 
53
#endif
 
54
static void flash_get_offsets (ulong base, flash_info_t *info);
 
55
 
 
56
 
 
57
/*-----------------------------------------------------------------------
 
58
 */
 
59
 
 
60
unsigned long flash_init (void)
 
61
{
 
62
        unsigned long size_b0, size_b1;
 
63
        int i;
 
64
        uint pbcr;
 
65
        unsigned long base_b0, base_b1;
 
66
 
 
67
        /* Init: no FLASHes known */
 
68
        for (i=0; i<CONFIG_SYS_MAX_FLASH_BANKS; ++i) {
 
69
                flash_info[i].flash_id = FLASH_UNKNOWN;
 
70
        }
 
71
 
 
72
        /* Static FLASH Bank configuration here - FIXME XXX */
 
73
 
 
74
        size_b0 = flash_get_size((volatile FLASH_WORD_SIZE *)FLASH_BASE1_PRELIM, &flash_info[0]);
 
75
 
 
76
        if (flash_info[0].flash_id == FLASH_UNKNOWN) {
 
77
                printf ("## Unknown FLASH on Bank 0 - Size = 0x%08lx = %ld MB\n",
 
78
                        size_b0, size_b0<<20);
 
79
        }
 
80
 
 
81
        /* Only one bank */
 
82
        if (CONFIG_SYS_MAX_FLASH_BANKS == 1) {
 
83
                /* Setup offsets */
 
84
                flash_get_offsets (FLASH_BASE1_PRELIM, &flash_info[0]);
 
85
 
 
86
                /* Monitor protection ON by default */
 
87
#if 0   /* sand: */
 
88
                (void)flash_protect(FLAG_PROTECT_SET,
 
89
                        FLASH_BASE1_PRELIM-CONFIG_SYS_MONITOR_LEN+size_b0,
 
90
                        FLASH_BASE1_PRELIM-1+size_b0,
 
91
                        &flash_info[0]);
 
92
#else
 
93
                (void)flash_protect(FLAG_PROTECT_SET,
 
94
                        CONFIG_SYS_MONITOR_BASE,
 
95
                        CONFIG_SYS_MONITOR_BASE+CONFIG_SYS_MONITOR_LEN-1,
 
96
                        &flash_info[0]);
 
97
#endif
 
98
                size_b1 = 0 ;
 
99
                flash_info[0].size = size_b0;
 
100
        } else {        /* 2 banks */
 
101
                size_b1 = flash_get_size((volatile FLASH_WORD_SIZE *)FLASH_BASE1_PRELIM, &flash_info[1]);
 
102
 
 
103
                /* Re-do sizing to get full correct info */
 
104
                if (size_b1) {
 
105
                        mtdcr(EBC0_CFGADDR, PB0CR);
 
106
                        pbcr = mfdcr(EBC0_CFGDATA);
 
107
                        mtdcr(EBC0_CFGADDR, PB0CR);
 
108
                        base_b1 = -size_b1;
 
109
                        pbcr = (pbcr & 0x0001ffff) | base_b1 | (((size_b1/1024/1024)-1)<<17);
 
110
                        mtdcr(EBC0_CFGDATA, pbcr);
 
111
                }
 
112
 
 
113
                if (size_b0) {
 
114
                        mtdcr(EBC0_CFGADDR, PB1CR);
 
115
                        pbcr = mfdcr(EBC0_CFGDATA);
 
116
                        mtdcr(EBC0_CFGADDR, PB1CR);
 
117
                        base_b0 = base_b1 - size_b0;
 
118
                        pbcr = (pbcr & 0x0001ffff) | base_b0 | (((size_b0/1024/1024)-1)<<17);
 
119
                        mtdcr(EBC0_CFGDATA, pbcr);
 
120
                }
 
121
 
 
122
                size_b0 = flash_get_size((volatile FLASH_WORD_SIZE *)base_b0, &flash_info[0]);
 
123
 
 
124
                flash_get_offsets (base_b0, &flash_info[0]);
 
125
 
 
126
                /* monitor protection ON by default */
 
127
#if 0   /* sand: */
 
128
                (void)flash_protect(FLAG_PROTECT_SET,
 
129
                        FLASH_BASE1_PRELIM-CONFIG_SYS_MONITOR_LEN+size_b0,
 
130
                        FLASH_BASE1_PRELIM-1+size_b0,
 
131
                        &flash_info[0]);
 
132
#else
 
133
                (void)flash_protect(FLAG_PROTECT_SET,
 
134
                        CONFIG_SYS_MONITOR_BASE,
 
135
                        CONFIG_SYS_MONITOR_BASE+CONFIG_SYS_MONITOR_LEN-1,
 
136
                        &flash_info[0]);
 
137
#endif
 
138
 
 
139
                if (size_b1) {
 
140
                        /* Re-do sizing to get full correct info */
 
141
                        size_b1 = flash_get_size((volatile FLASH_WORD_SIZE *)base_b1, &flash_info[1]);
 
142
 
 
143
                        flash_get_offsets (base_b1, &flash_info[1]);
 
144
 
 
145
                        /* monitor protection ON by default */
 
146
                        (void)flash_protect(FLAG_PROTECT_SET,
 
147
                                base_b1+size_b1-CONFIG_SYS_MONITOR_LEN,
 
148
                                base_b1+size_b1-1,
 
149
                                &flash_info[1]);
 
150
                        /* monitor protection OFF by default (one is enough) */
 
151
                        (void)flash_protect(FLAG_PROTECT_CLEAR,
 
152
                                base_b0+size_b0-CONFIG_SYS_MONITOR_LEN,
 
153
                                base_b0+size_b0-1,
 
154
                                &flash_info[0]);
 
155
                } else {
 
156
                        flash_info[1].flash_id = FLASH_UNKNOWN;
 
157
                        flash_info[1].sector_count = -1;
 
158
                }
 
159
 
 
160
                flash_info[0].size = size_b0;
 
161
                flash_info[1].size = size_b1;
 
162
        }/* else 2 banks */
 
163
        return (size_b0 + size_b1);
 
164
}
 
165
 
 
166
 
 
167
/*-----------------------------------------------------------------------
 
168
 */
 
169
 
 
170
static void flash_get_offsets (ulong base, flash_info_t *info)
 
171
{
 
172
        int i;
 
173
 
 
174
        /* set up sector start adress table */
 
175
        if ((info->flash_id & FLASH_TYPEMASK) == INTEL_ID_28F320J3A ||
 
176
                (info->flash_id & FLASH_TYPEMASK) == INTEL_ID_28F640J3A ||
 
177
                (info->flash_id & FLASH_TYPEMASK) == INTEL_ID_28F128J3A) {
 
178
                for (i = 0; i < info->sector_count; i++) {
 
179
                        info->start[i] = base + (i * info->size/info->sector_count);
 
180
                }
 
181
        }
 
182
        else if (info->flash_id & FLASH_BTYPE) {
 
183
                if ((info->flash_id & FLASH_VENDMASK) == FLASH_MAN_INTEL) {
 
184
 
 
185
#ifndef CONFIG_SYS_FLASH_16BIT
 
186
                        /* set sector offsets for bottom boot block type */
 
187
                        info->start[0] = base + 0x00000000;
 
188
                        info->start[1] = base + 0x00004000;
 
189
                        info->start[2] = base + 0x00008000;
 
190
                        info->start[3] = base + 0x0000C000;
 
191
                        info->start[4] = base + 0x00010000;
 
192
                        info->start[5] = base + 0x00014000;
 
193
                        info->start[6] = base + 0x00018000;
 
194
                        info->start[7] = base + 0x0001C000;
 
195
                        for (i = 8; i < info->sector_count; i++) {
 
196
                                info->start[i] = base + (i * 0x00020000) - 0x000E0000;
 
197
                        }
 
198
                } else {
 
199
                        /* set sector offsets for bottom boot block type */
 
200
                        info->start[0] = base + 0x00000000;
 
201
                        info->start[1] = base + 0x00008000;
 
202
                        info->start[2] = base + 0x0000C000;
 
203
                        info->start[3] = base + 0x00010000;
 
204
                        for (i = 4; i < info->sector_count; i++) {
 
205
                                info->start[i] = base + (i * 0x00020000) - 0x00060000;
 
206
                        }
 
207
                }
 
208
#else
 
209
                        /* set sector offsets for bottom boot block type */
 
210
                        info->start[0] = base + 0x00000000;
 
211
                        info->start[1] = base + 0x00002000;
 
212
                        info->start[2] = base + 0x00004000;
 
213
                        info->start[3] = base + 0x00006000;
 
214
                        info->start[4] = base + 0x00008000;
 
215
                        info->start[5] = base + 0x0000A000;
 
216
                        info->start[6] = base + 0x0000C000;
 
217
                        info->start[7] = base + 0x0000E000;
 
218
                        for (i = 8; i < info->sector_count; i++) {
 
219
                                info->start[i] = base + (i * 0x00010000) - 0x00070000;
 
220
                        }
 
221
                } else {
 
222
                        /* set sector offsets for bottom boot block type */
 
223
                        info->start[0] = base + 0x00000000;
 
224
                        info->start[1] = base + 0x00004000;
 
225
                        info->start[2] = base + 0x00006000;
 
226
                        info->start[3] = base + 0x00008000;
 
227
                        for (i = 4; i < info->sector_count; i++) {
 
228
                                info->start[i] = base + (i * 0x00010000) - 0x00030000;
 
229
                        }
 
230
                }
 
231
#endif
 
232
        } else {
 
233
                /* set sector offsets for top boot block type */
 
234
                i = info->sector_count - 1;
 
235
                if ((info->flash_id & FLASH_VENDMASK) == FLASH_MAN_INTEL) {
 
236
 
 
237
#ifndef CONFIG_SYS_FLASH_16BIT
 
238
                        info->start[i--] = base + info->size - 0x00004000;
 
239
                        info->start[i--] = base + info->size - 0x00008000;
 
240
                        info->start[i--] = base + info->size - 0x0000C000;
 
241
                        info->start[i--] = base + info->size - 0x00010000;
 
242
                        info->start[i--] = base + info->size - 0x00014000;
 
243
                        info->start[i--] = base + info->size - 0x00018000;
 
244
                        info->start[i--] = base + info->size - 0x0001C000;
 
245
                        for (; i >= 0; i--) {
 
246
                                info->start[i] = base + i * 0x00020000;
 
247
                        }
 
248
                } else {
 
249
 
 
250
                        info->start[i--] = base + info->size - 0x00008000;
 
251
                        info->start[i--] = base + info->size - 0x0000C000;
 
252
                        info->start[i--] = base + info->size - 0x00010000;
 
253
                        for (; i >= 0; i--) {
 
254
                                info->start[i] = base + i * 0x00020000;
 
255
                        }
 
256
                }
 
257
#else
 
258
                        info->start[i--] = base + info->size - 0x00002000;
 
259
                        info->start[i--] = base + info->size - 0x00004000;
 
260
                        info->start[i--] = base + info->size - 0x00006000;
 
261
                        info->start[i--] = base + info->size - 0x00008000;
 
262
                        info->start[i--] = base + info->size - 0x0000A000;
 
263
                        info->start[i--] = base + info->size - 0x0000C000;
 
264
                        info->start[i--] = base + info->size - 0x0000E000;
 
265
                        for (; i >= 0; i--) {
 
266
                                info->start[i] = base + i * 0x00010000;
 
267
                        }
 
268
                } else {
 
269
                        info->start[i--] = base + info->size - 0x00004000;
 
270
                        info->start[i--] = base + info->size - 0x00006000;
 
271
                        info->start[i--] = base + info->size - 0x00008000;
 
272
                        for (; i >= 0; i--) {
 
273
                                info->start[i] = base + i * 0x00010000;
 
274
                        }
 
275
                }
 
276
#endif
 
277
        }
 
278
}
 
279
 
 
280
/*-----------------------------------------------------------------------
 
281
 */
 
282
 
 
283
void flash_print_info  (flash_info_t *info)
 
284
{
 
285
        int i;
 
286
        uchar *boottype;
 
287
        uchar botboot[]=", bottom boot sect)\n";
 
288
        uchar topboot[]=", top boot sector)\n";
 
289
 
 
290
        if (info->flash_id == FLASH_UNKNOWN) {
 
291
                printf ("missing or unknown FLASH type\n");
 
292
                return;
 
293
        }
 
294
 
 
295
        switch (info->flash_id & FLASH_VENDMASK) {
 
296
        case FLASH_MAN_AMD:     printf ("AMD ");                break;
 
297
        case FLASH_MAN_FUJ:     printf ("FUJITSU ");            break;
 
298
        case FLASH_MAN_SST:     printf ("SST ");                break;
 
299
        case FLASH_MAN_STM:     printf ("STM ");                break;
 
300
        case FLASH_MAN_INTEL:   printf ("INTEL ");              break;
 
301
        default:                printf ("Unknown Vendor ");     break;
 
302
        }
 
303
 
 
304
        if (info->flash_id & 0x0001 ) {
 
305
                boottype = botboot;
 
306
        } else {
 
307
                boottype = topboot;
 
308
        }
 
309
 
 
310
        switch (info->flash_id & FLASH_TYPEMASK) {
 
311
        case FLASH_AM400B:      printf ("AM29LV400B (4 Mbit%s",boottype);
 
312
                                break;
 
313
        case FLASH_AM400T:      printf ("AM29LV400T (4 Mbit%s",boottype);
 
314
                                break;
 
315
        case FLASH_AM800B:      printf ("AM29LV800B (8 Mbit%s",boottype);
 
316
                                break;
 
317
        case FLASH_AM800T:      printf ("AM29LV800T (8 Mbit%s",boottype);
 
318
                                break;
 
319
        case FLASH_AM160B:      printf ("AM29LV160B (16 Mbit%s",boottype);
 
320
                                break;
 
321
        case FLASH_AM160T:      printf ("AM29LV160T (16 Mbit%s",boottype);
 
322
                                break;
 
323
        case FLASH_AM320B:      printf ("AM29LV320B (32 Mbit%s",boottype);
 
324
                                break;
 
325
        case FLASH_AM320T:      printf ("AM29LV320T (32 Mbit%s",boottype);
 
326
                                break;
 
327
        case FLASH_INTEL800B:   printf ("INTEL28F800B (8 Mbit%s",boottype);
 
328
                                break;
 
329
        case FLASH_INTEL800T:   printf ("INTEL28F800T (8 Mbit%s",boottype);
 
330
                                break;
 
331
        case FLASH_INTEL160B:   printf ("INTEL28F160B (16 Mbit%s",boottype);
 
332
                                break;
 
333
        case FLASH_INTEL160T:   printf ("INTEL28F160T (16 Mbit%s",boottype);
 
334
                                break;
 
335
        case FLASH_INTEL320B:   printf ("INTEL28F320B (32 Mbit%s",boottype);
 
336
                                break;
 
337
        case FLASH_INTEL320T:   printf ("INTEL28F320T (32 Mbit%s",boottype);
 
338
                                break;
 
339
        case FLASH_AMDL322T:    printf ("AM29DL322T (32 Mbit%s",boottype);
 
340
                                break;
 
341
 
 
342
#if 0 /* enable when devices are available */
 
343
 
 
344
        case FLASH_INTEL640B:   printf ("INTEL28F640B (64 Mbit%s",boottype);
 
345
                                break;
 
346
        case FLASH_INTEL640T:   printf ("INTEL28F640T (64 Mbit%s",boottype);
 
347
                                break;
 
348
#endif
 
349
        case INTEL_ID_28F320J3A:        printf ("INTEL28F320JA3 (32 Mbit%s",boottype);
 
350
                                break;
 
351
        case INTEL_ID_28F640J3A:        printf ("INTEL28F640JA3 (64 Mbit%s",boottype);
 
352
                                break;
 
353
        case INTEL_ID_28F128J3A:        printf ("INTEL28F128JA3 (128 Mbit%s",boottype);
 
354
                                break;
 
355
 
 
356
        default:                printf ("Unknown Chip Type\n");
 
357
                                break;
 
358
        }
 
359
 
 
360
        printf ("  Size: %ld MB in %d Sectors\n",
 
361
                info->size >> 20, info->sector_count);
 
362
 
 
363
        printf ("  Sector Start Addresses:");
 
364
        for (i=0; i<info->sector_count; ++i) {
 
365
                if ((i % 5) == 0)
 
366
                        printf ("\n   ");
 
367
                printf (" %08lX%s",
 
368
                        info->start[i],
 
369
                        info->protect[i] ? " (RO)" : "     "
 
370
                );
 
371
        }
 
372
        printf ("\n");
 
373
        return;
 
374
}
 
375
 
 
376
 
 
377
/*-----------------------------------------------------------------------
 
378
 */
 
379
 
 
380
 
 
381
/*-----------------------------------------------------------------------
 
382
 */
 
383
 
 
384
/*
 
385
 * The following code cannot be run from FLASH!
 
386
 */
 
387
ulong flash_get_size (volatile FLASH_WORD_SIZE *addr, flash_info_t *info)
 
388
{
 
389
        short i;
 
390
        ulong base = (ulong)addr;
 
391
        FLASH_WORD_SIZE value;
 
392
 
 
393
        /* Write auto select command: read Manufacturer ID */
 
394
 
 
395
 
 
396
#ifndef CONFIG_SYS_FLASH_16BIT
 
397
 
 
398
        /*
 
399
         * Note: if it is an AMD flash and the word at addr[0000]
 
400
         * is 0x00890089 this routine will think it is an Intel
 
401
         * flash device and may(most likely) cause trouble.
 
402
         */
 
403
 
 
404
        addr[0x0000] = 0x00900090;
 
405
        if(addr[0x0000] != 0x00890089){
 
406
                addr[0x0555] = 0x00AA00AA;
 
407
                addr[0x02AA] = 0x00550055;
 
408
                addr[0x0555] = 0x00900090;
 
409
#else
 
410
 
 
411
        /*
 
412
         * Note: if it is an AMD flash and the word at addr[0000]
 
413
         * is 0x0089 this routine will think it is an Intel
 
414
         * flash device and may(most likely) cause trouble.
 
415
         */
 
416
 
 
417
        addr[0x0000] = 0x0090;
 
418
 
 
419
        if(addr[0x0000] != 0x0089){
 
420
                addr[0x0555] = 0x00AA;
 
421
                addr[0x02AA] = 0x0055;
 
422
                addr[0x0555] = 0x0090;
 
423
#endif
 
424
        }
 
425
        value = addr[0];
 
426
 
 
427
        switch (value) {
 
428
        case (AMD_MANUFACT & FLASH_ID_MASK):
 
429
                info->flash_id = FLASH_MAN_AMD;
 
430
                break;
 
431
        case (FUJ_MANUFACT & FLASH_ID_MASK):
 
432
                info->flash_id = FLASH_MAN_FUJ;
 
433
                break;
 
434
        case (STM_MANUFACT & FLASH_ID_MASK):
 
435
                info->flash_id = FLASH_MAN_STM;
 
436
                break;
 
437
        case (SST_MANUFACT & FLASH_ID_MASK):
 
438
                info->flash_id = FLASH_MAN_SST;
 
439
                break;
 
440
        case (INTEL_MANUFACT & FLASH_ID_MASK):
 
441
                info->flash_id = FLASH_MAN_INTEL;
 
442
                break;
 
443
        default:
 
444
                info->flash_id = FLASH_UNKNOWN;
 
445
                info->sector_count = 0;
 
446
                info->size = 0;
 
447
                return (0); /* no or unknown flash */
 
448
 
 
449
        }
 
450
 
 
451
        value = addr[1];                        /* device ID            */
 
452
 
 
453
        switch (value) {
 
454
 
 
455
        case (AMD_ID_LV400T & FLASH_ID_MASK):
 
456
                info->flash_id += FLASH_AM400T;
 
457
                info->sector_count = 11;
 
458
                info->size = 0x00100000;
 
459
                break;                          /* => 1 MB              */
 
460
 
 
461
        case (AMD_ID_LV400B & FLASH_ID_MASK):
 
462
                info->flash_id += FLASH_AM400B;
 
463
                info->sector_count = 11;
 
464
                info->size = 0x00100000;
 
465
                break;                          /* => 1 MB              */
 
466
 
 
467
        case (AMD_ID_LV800T & FLASH_ID_MASK):
 
468
                info->flash_id += FLASH_AM800T;
 
469
                info->sector_count = 19;
 
470
                info->size = 0x00200000;
 
471
                break;                          /* => 2 MB              */
 
472
 
 
473
        case (AMD_ID_LV800B & FLASH_ID_MASK):
 
474
                info->flash_id += FLASH_AM800B;
 
475
                info->sector_count = 19;
 
476
                info->size = 0x00200000;
 
477
                break;                          /* => 2 MB              */
 
478
 
 
479
        case (AMD_ID_LV160T & FLASH_ID_MASK):
 
480
                info->flash_id += FLASH_AM160T;
 
481
                info->sector_count = 35;
 
482
                info->size = 0x00400000;
 
483
                break;                          /* => 4 MB              */
 
484
 
 
485
        case (AMD_ID_LV160B & FLASH_ID_MASK):
 
486
                info->flash_id += FLASH_AM160B;
 
487
                info->sector_count = 35;
 
488
                info->size = 0x00400000;
 
489
                break;                          /* => 4 MB              */
 
490
#if 0   /* enable when device IDs are available */
 
491
        case (AMD_ID_LV320T & FLASH_ID_MASK):
 
492
                info->flash_id += FLASH_AM320T;
 
493
                info->sector_count = 67;
 
494
                info->size = 0x00800000;
 
495
                break;                          /* => 8 MB              */
 
496
 
 
497
        case (AMD_ID_LV320B & FLASH_ID_MASK):
 
498
                info->flash_id += FLASH_AM320B;
 
499
                info->sector_count = 67;
 
500
                info->size = 0x00800000;
 
501
                break;                          /* => 8 MB              */
 
502
#endif
 
503
 
 
504
        case (AMD_ID_DL322T & FLASH_ID_MASK):
 
505
                info->flash_id += FLASH_AMDL322T;
 
506
                info->sector_count = 71;
 
507
                info->size = 0x00800000;
 
508
                break;                          /* => 8 MB              */
 
509
 
 
510
        case (INTEL_ID_28F800B3T & FLASH_ID_MASK):
 
511
                info->flash_id += FLASH_INTEL800T;
 
512
                info->sector_count = 23;
 
513
                info->size = 0x00200000;
 
514
                break;                          /* => 2 MB              */
 
515
 
 
516
        case (INTEL_ID_28F800B3B & FLASH_ID_MASK):
 
517
                info->flash_id += FLASH_INTEL800B;
 
518
                info->sector_count = 23;
 
519
                info->size = 0x00200000;
 
520
                break;                          /* => 2 MB              */
 
521
 
 
522
        case (INTEL_ID_28F160B3T & FLASH_ID_MASK):
 
523
                info->flash_id += FLASH_INTEL160T;
 
524
                info->sector_count = 39;
 
525
                info->size = 0x00400000;
 
526
                break;                          /* => 4 MB              */
 
527
 
 
528
        case (INTEL_ID_28F160B3B & FLASH_ID_MASK):
 
529
                info->flash_id += FLASH_INTEL160B;
 
530
                info->sector_count = 39;
 
531
                info->size = 0x00400000;
 
532
                break;                          /* => 4 MB              */
 
533
 
 
534
        case (INTEL_ID_28F320B3T & FLASH_ID_MASK):
 
535
                info->flash_id += FLASH_INTEL320T;
 
536
                info->sector_count = 71;
 
537
                info->size = 0x00800000;
 
538
                break;                          /* => 8 MB              */
 
539
 
 
540
        case (INTEL_ID_28F320B3B & FLASH_ID_MASK):
 
541
                info->flash_id += FLASH_AM320B;
 
542
                info->sector_count = 71;
 
543
                info->size = 0x00800000;
 
544
                break;                          /* => 8 MB              */
 
545
 
 
546
#if 0 /* enable when devices are available */
 
547
        case (INTEL_ID_28F320B3T & FLASH_ID_MASK):
 
548
                info->flash_id += FLASH_INTEL320T;
 
549
                info->sector_count = 135;
 
550
                info->size = 0x01000000;
 
551
                break;                          /* => 16 MB             */
 
552
 
 
553
        case (INTEL_ID_28F320B3B & FLASH_ID_MASK):
 
554
                info->flash_id += FLASH_AM320B;
 
555
                info->sector_count = 135;
 
556
                info->size = 0x01000000;
 
557
                break;                          /* => 16 MB             */
 
558
#endif
 
559
        case (INTEL_ID_28F320J3A & FLASH_ID_MASK):
 
560
                info->flash_id += FLASH_28F320J3A;
 
561
                info->sector_count = 32;
 
562
                info->size = 0x00400000;
 
563
                break;                          /* => 32 MBit   */
 
564
        case (INTEL_ID_28F640J3A & FLASH_ID_MASK):
 
565
                info->flash_id += FLASH_28F640J3A;
 
566
                info->sector_count = 64;
 
567
                info->size = 0x00800000;
 
568
                break;                          /* => 64 MBit   */
 
569
        case (INTEL_ID_28F128J3A & FLASH_ID_MASK):
 
570
                info->flash_id += FLASH_28F128J3A;
 
571
                info->sector_count = 128;
 
572
                info->size = 0x01000000;
 
573
                break;                          /* => 128 MBit  */
 
574
 
 
575
        default:
 
576
                /* FIXME*/
 
577
                info->flash_id = FLASH_UNKNOWN;
 
578
                return (0);                     /* => no or unknown flash */
 
579
        }
 
580
 
 
581
        flash_get_offsets(base, info);
 
582
 
 
583
        /* check for protected sectors */
 
584
        for (i = 0; i < info->sector_count; i++) {
 
585
                /* read sector protection at sector address, (A7 .. A0) = 0x02 */
 
586
                /* D0 = 1 if protected */
 
587
                addr = (volatile FLASH_WORD_SIZE *)(info->start[i]);
 
588
                info->protect[i] = addr[2] & 1;
 
589
        }
 
590
 
 
591
        /*
 
592
         * Prevent writes to uninitialized FLASH.
 
593
         */
 
594
        if (info->flash_id != FLASH_UNKNOWN) {
 
595
                addr = (volatile FLASH_WORD_SIZE *)info->start[0];
 
596
                if( (info->flash_id & 0xFF00) == FLASH_MAN_INTEL){
 
597
                        *addr = (0x00F000F0 & FLASH_ID_MASK);   /* reset bank */
 
598
                } else {
 
599
                        *addr = (0x00FF00FF & FLASH_ID_MASK);   /* reset bank */
 
600
                }
 
601
        }
 
602
 
 
603
        return (info->size);
 
604
}
 
605
 
 
606
 
 
607
/*-----------------------------------------------------------------------
 
608
 */
 
609
 
 
610
int flash_erase (flash_info_t * info, int s_first, int s_last)
 
611
{
 
612
 
 
613
        volatile FLASH_WORD_SIZE *addr =
 
614
                (volatile FLASH_WORD_SIZE *) (info->start[0]);
 
615
        int flag, prot, sect, l_sect, barf;
 
616
        ulong start, now, last;
 
617
        int rcode = 0;
 
618
 
 
619
        if ((s_first < 0) || (s_first > s_last)) {
 
620
                if (info->flash_id == FLASH_UNKNOWN) {
 
621
                        printf ("- missing\n");
 
622
                } else {
 
623
                        printf ("- no sectors to erase\n");
 
624
                }
 
625
                return 1;
 
626
        }
 
627
 
 
628
        if ((info->flash_id == FLASH_UNKNOWN) ||
 
629
            ((info->flash_id > FLASH_AMD_COMP) &&
 
630
             ((info->flash_id & FLASH_VENDMASK) != FLASH_MAN_INTEL))) {
 
631
                printf ("Can't erase unknown flash type - aborted\n");
 
632
                return 1;
 
633
        }
 
634
 
 
635
        prot = 0;
 
636
        for (sect = s_first; sect <= s_last; ++sect) {
 
637
                if (info->protect[sect]) {
 
638
                        prot++;
 
639
                }
 
640
        }
 
641
 
 
642
        if (prot) {
 
643
                printf ("- Warning: %d protected sectors will not be erased!\n", prot);
 
644
        } else {
 
645
                printf ("\n");
 
646
        }
 
647
 
 
648
        l_sect = -1;
 
649
 
 
650
        /* Disable interrupts which might cause a timeout here */
 
651
        flag = disable_interrupts ();
 
652
        if (info->flash_id < FLASH_AMD_COMP) {
 
653
#ifndef CONFIG_SYS_FLASH_16BIT
 
654
                addr[0x0555] = 0x00AA00AA;
 
655
                addr[0x02AA] = 0x00550055;
 
656
                addr[0x0555] = 0x00800080;
 
657
                addr[0x0555] = 0x00AA00AA;
 
658
                addr[0x02AA] = 0x00550055;
 
659
#else
 
660
                addr[0x0555] = 0x00AA;
 
661
                addr[0x02AA] = 0x0055;
 
662
                addr[0x0555] = 0x0080;
 
663
                addr[0x0555] = 0x00AA;
 
664
                addr[0x02AA] = 0x0055;
 
665
#endif
 
666
                /* Start erase on unprotected sectors */
 
667
                for (sect = s_first; sect <= s_last; sect++) {
 
668
                        if (info->protect[sect] == 0) { /* not protected */
 
669
                                addr = (volatile FLASH_WORD_SIZE *) (info->start[sect]);
 
670
                                addr[0] = (0x00300030 & FLASH_ID_MASK);
 
671
                                l_sect = sect;
 
672
                        }
 
673
                }
 
674
 
 
675
                /* re-enable interrupts if necessary */
 
676
                if (flag)
 
677
                        enable_interrupts ();
 
678
 
 
679
                /* wait at least 80us - let's wait 1 ms */
 
680
                udelay (1000);
 
681
 
 
682
                /*
 
683
                 * We wait for the last triggered sector
 
684
                 */
 
685
                if (l_sect < 0)
 
686
                        goto DONE;
 
687
 
 
688
                start = get_timer (0);
 
689
                last = start;
 
690
                addr = (volatile FLASH_WORD_SIZE *) (info->start[l_sect]);
 
691
                while ((addr[0] & (0x00800080 & FLASH_ID_MASK)) !=
 
692
                       (0x00800080 & FLASH_ID_MASK)) {
 
693
                        if ((now = get_timer (start)) > CONFIG_SYS_FLASH_ERASE_TOUT) {
 
694
                                printf ("Timeout\n");
 
695
                                return 1;
 
696
                        }
 
697
                        /* show that we're waiting */
 
698
                        if ((now - last) > 1000) {      /* every second */
 
699
                                serial_putc ('.');
 
700
                                last = now;
 
701
                        }
 
702
                }
 
703
 
 
704
              DONE:
 
705
                /* reset to read mode */
 
706
                addr = (volatile FLASH_WORD_SIZE *) info->start[0];
 
707
                addr[0] = (0x00F000F0 & FLASH_ID_MASK); /* reset bank */
 
708
        } else {
 
709
 
 
710
 
 
711
                for (sect = s_first; sect <= s_last; sect++) {
 
712
                        if (info->protect[sect] == 0) { /* not protected */
 
713
                                barf = 0;
 
714
#ifndef CONFIG_SYS_FLASH_16BIT
 
715
                                addr = (vu_long *) (info->start[sect]);
 
716
                                addr[0] = 0x00200020;
 
717
                                addr[0] = 0x00D000D0;
 
718
                                while (!(addr[0] & 0x00800080));        /* wait for error or finish */
 
719
                                if (addr[0] & 0x003A003A) {     /* check for error */
 
720
                                        barf = addr[0] & 0x003A0000;
 
721
                                        if (barf) {
 
722
                                                barf >>= 16;
 
723
                                        } else {
 
724
                                                barf = addr[0] & 0x0000003A;
 
725
                                        }
 
726
                                }
 
727
#else
 
728
                                addr = (vu_short *) (info->start[sect]);
 
729
                                addr[0] = 0x0020;
 
730
                                addr[0] = 0x00D0;
 
731
                                while (!(addr[0] & 0x0080));    /* wait for error or finish */
 
732
                                if (addr[0] & 0x003A)   /* check for error */
 
733
                                        barf = addr[0] & 0x003A;
 
734
#endif
 
735
                                if (barf) {
 
736
                                        printf ("\nFlash error in sector at %lx\n",
 
737
                                                (unsigned long) addr);
 
738
                                        if (barf & 0x0002)
 
739
                                                printf ("Block locked, not erased.\n");
 
740
                                        if ((barf & 0x0030) == 0x0030)
 
741
                                                printf ("Command Sequence error.\n");
 
742
                                        if ((barf & 0x0030) == 0x0020)
 
743
                                                printf ("Block Erase error.\n");
 
744
                                        if (barf & 0x0008)
 
745
                                                printf ("Vpp Low error.\n");
 
746
                                        rcode = 1;
 
747
                                } else
 
748
                                        printf (".");
 
749
                                l_sect = sect;
 
750
                        }
 
751
                        addr = (volatile FLASH_WORD_SIZE *) info->start[0];
 
752
                        addr[0] = (0x00FF00FF & FLASH_ID_MASK); /* reset bank */
 
753
 
 
754
                }
 
755
 
 
756
        }
 
757
        printf (" done\n");
 
758
        return rcode;
 
759
}
 
760
 
 
761
/*-----------------------------------------------------------------------
 
762
 */
 
763
 
 
764
/*flash_info_t *addr2info (ulong addr)
 
765
{
 
766
        flash_info_t *info;
 
767
        int i;
 
768
 
 
769
        for (i=0, info=&flash_info[0]; i<CONFIG_SYS_MAX_FLASH_BANKS; ++i, ++info) {
 
770
                if ((addr >= info->start[0]) &&
 
771
                    (addr < (info->start[0] + info->size)) ) {
 
772
                        return (info);
 
773
                }
 
774
        }
 
775
 
 
776
        return (NULL);
 
777
}
 
778
*/
 
779
/*-----------------------------------------------------------------------
 
780
 * Copy memory to flash.
 
781
 * Make sure all target addresses are within Flash bounds,
 
782
 * and no protected sectors are hit.
 
783
 * Returns:
 
784
 * 0 - OK
 
785
 * 1 - write timeout
 
786
 * 2 - Flash not erased
 
787
 * 4 - target range includes protected sectors
 
788
 * 8 - target address not in Flash memory
 
789
 */
 
790
 
 
791
/*int flash_write (uchar *src, ulong addr, ulong cnt)
 
792
{
 
793
        int i;
 
794
        ulong         end        = addr + cnt - 1;
 
795
        flash_info_t *info_first = addr2info (addr);
 
796
        flash_info_t *info_last  = addr2info (end );
 
797
        flash_info_t *info;
 
798
 
 
799
        if (cnt == 0) {
 
800
                return (0);
 
801
        }
 
802
 
 
803
        if (!info_first || !info_last) {
 
804
                return (8);
 
805
        }
 
806
 
 
807
        for (info = info_first; info <= info_last; ++info) {
 
808
                ulong b_end = info->start[0] + info->size;*/    /* bank end addr */
 
809
/*              short s_end = info->sector_count - 1;
 
810
                for (i=0; i<info->sector_count; ++i) {
 
811
                        ulong e_addr = (i == s_end) ? b_end : info->start[i + 1];
 
812
 
 
813
                        if ((end >= info->start[i]) && (addr < e_addr) &&
 
814
                            (info->protect[i] != 0) ) {
 
815
                                return (4);
 
816
                        }
 
817
                }
 
818
        }
 
819
 
 
820
*/      /* finally write data to flash */
 
821
/*      for (info = info_first; info <= info_last && cnt>0; ++info) {
 
822
                ulong len;
 
823
 
 
824
                len = info->start[0] + info->size - addr;
 
825
                if (len > cnt)
 
826
                        len = cnt;
 
827
                if ((i = write_buff(info, src, addr, len)) != 0) {
 
828
                        return (i);
 
829
                }
 
830
                cnt  -= len;
 
831
                addr += len;
 
832
                src  += len;
 
833
        }
 
834
        return (0);
 
835
}
 
836
*/
 
837
/*-----------------------------------------------------------------------
 
838
 * Copy memory to flash, returns:
 
839
 * 0 - OK
 
840
 * 1 - write timeout
 
841
 * 2 - Flash not erased
 
842
 */
 
843
 
 
844
int write_buff (flash_info_t *info, uchar *src, ulong addr, ulong cnt)
 
845
{
 
846
#ifndef CONFIG_SYS_FLASH_16BIT
 
847
        ulong cp, wp, data;
 
848
        int l;
 
849
#else
 
850
        ulong cp, wp;
 
851
        ushort data;
 
852
#endif
 
853
        int i, rc;
 
854
 
 
855
#ifndef CONFIG_SYS_FLASH_16BIT
 
856
 
 
857
 
 
858
        wp = (addr & ~3);       /* get lower word aligned address */
 
859
 
 
860
        /*
 
861
         * handle unaligned start bytes
 
862
         */
 
863
        if ((l = addr - wp) != 0) {
 
864
                data = 0;
 
865
                for (i=0, cp=wp; i<l; ++i, ++cp) {
 
866
                        data = (data << 8) | (*(uchar *)cp);
 
867
                }
 
868
                for (; i<4 && cnt>0; ++i) {
 
869
                        data = (data << 8) | *src++;
 
870
                        --cnt;
 
871
                        ++cp;
 
872
                }
 
873
                for (; cnt==0 && i<4; ++i, ++cp) {
 
874
                        data = (data << 8) | (*(uchar *)cp);
 
875
                }
 
876
 
 
877
                if ((rc = write_word(info, wp, data)) != 0) {
 
878
                        return (rc);
 
879
                }
 
880
                wp += 4;
 
881
        }
 
882
 
 
883
        /*
 
884
         * handle word aligned part
 
885
         */
 
886
        while (cnt >= 4) {
 
887
                data = 0;
 
888
                for (i=0; i<4; ++i) {
 
889
                        data = (data << 8) | *src++;
 
890
                }
 
891
                if ((rc = write_word(info, wp, data)) != 0) {
 
892
                        return (rc);
 
893
                }
 
894
                wp  += 4;
 
895
                cnt -= 4;
 
896
        }
 
897
 
 
898
        if (cnt == 0) {
 
899
                return (0);
 
900
        }
 
901
 
 
902
        /*
 
903
         * handle unaligned tail bytes
 
904
         */
 
905
        data = 0;
 
906
        for (i=0, cp=wp; i<4 && cnt>0; ++i, ++cp) {
 
907
                data = (data << 8) | *src++;
 
908
                --cnt;
 
909
        }
 
910
        for (; i<4; ++i, ++cp) {
 
911
                data = (data << 8) | (*(uchar *)cp);
 
912
        }
 
913
 
 
914
        return (write_word(info, wp, data));
 
915
 
 
916
#else
 
917
        wp = (addr & ~1);       /* get lower word aligned address */
 
918
 
 
919
        /*
 
920
         * handle unaligned start byte
 
921
         */
 
922
        if (addr - wp) {
 
923
                data = 0;
 
924
                data = (data << 8) | *src++;
 
925
                --cnt;
 
926
                if ((rc = write_short(info, wp, data)) != 0) {
 
927
                        return (rc);
 
928
                }
 
929
                wp += 2;
 
930
        }
 
931
 
 
932
        /*
 
933
         * handle word aligned part
 
934
         */
 
935
/*      l = 0; used for debuging  */
 
936
        while (cnt >= 2) {
 
937
                data = 0;
 
938
                for (i=0; i<2; ++i) {
 
939
                        data = (data << 8) | *src++;
 
940
                }
 
941
 
 
942
/*              if(!l){
 
943
                        printf("%x",data);
 
944
                        l = 1;
 
945
                }  used for debuging */
 
946
 
 
947
                if ((rc = write_short(info, wp, data)) != 0) {
 
948
                        return (rc);
 
949
                }
 
950
                wp  += 2;
 
951
                cnt -= 2;
 
952
        }
 
953
 
 
954
        if (cnt == 0) {
 
955
                return (0);
 
956
        }
 
957
 
 
958
        /*
 
959
         * handle unaligned tail bytes
 
960
         */
 
961
        data = 0;
 
962
        for (i=0, cp=wp; i<2 && cnt>0; ++i, ++cp) {
 
963
                data = (data << 8) | *src++;
 
964
                --cnt;
 
965
        }
 
966
        for (; i<2; ++i, ++cp) {
 
967
                data = (data << 8) | (*(uchar *)cp);
 
968
        }
 
969
 
 
970
        return (write_short(info, wp, data));
 
971
 
 
972
 
 
973
#endif
 
974
}
 
975
 
 
976
/*-----------------------------------------------------------------------
 
977
 * Write a word to Flash, returns:
 
978
 * 0 - OK
 
979
 * 1 - write timeout
 
980
 * 2 - Flash not erased
 
981
 */
 
982
#ifndef CONFIG_SYS_FLASH_16BIT
 
983
static int write_word (flash_info_t *info, ulong dest, ulong data)
 
984
{
 
985
        vu_long *addr = (vu_long*)(info->start[0]);
 
986
        ulong start,barf;
 
987
        int flag;
 
988
 
 
989
 
 
990
        /* Check if Flash is (sufficiently) erased */
 
991
        if ((*((vu_long *)dest) & data) != data) {
 
992
                return (2);
 
993
        }
 
994
 
 
995
        /* Disable interrupts which might cause a timeout here */
 
996
        flag = disable_interrupts();
 
997
 
 
998
        if(info->flash_id > FLASH_AMD_COMP) {
 
999
                /* AMD stuff */
 
1000
                addr[0x0555] = 0x00AA00AA;
 
1001
                addr[0x02AA] = 0x00550055;
 
1002
                addr[0x0555] = 0x00A000A0;
 
1003
        } else {
 
1004
                /* intel stuff */
 
1005
                *addr = 0x00400040;
 
1006
        }
 
1007
        *((vu_long *)dest) = data;
 
1008
 
 
1009
        /* re-enable interrupts if necessary */
 
1010
        if (flag)
 
1011
                enable_interrupts();
 
1012
 
 
1013
        /* data polling for D7 */
 
1014
        start = get_timer (0);
 
1015
 
 
1016
        if(info->flash_id > FLASH_AMD_COMP) {
 
1017
                while ((*((vu_long *)dest) & 0x00800080) != (data & 0x00800080)) {
 
1018
                        if (get_timer(start) > CONFIG_SYS_FLASH_WRITE_TOUT) {
 
1019
                                return (1);
 
1020
                        }
 
1021
                }
 
1022
        } else {
 
1023
                while(!(addr[0] & 0x00800080)) {        /* wait for error or finish */
 
1024
                        if (get_timer(start) > CONFIG_SYS_FLASH_WRITE_TOUT) {
 
1025
                                return (1);
 
1026
                        }
 
1027
 
 
1028
                if( addr[0] & 0x003A003A) {     /* check for error */
 
1029
                        barf = addr[0] & 0x003A0000;
 
1030
                        if( barf ) {
 
1031
                                barf >>=16;
 
1032
                        } else {
 
1033
                                barf = addr[0] & 0x0000003A;
 
1034
                        }
 
1035
                        printf("\nFlash write error at address %lx\n",(unsigned long)dest);
 
1036
                        if(barf & 0x0002) printf("Block locked, not erased.\n");
 
1037
                        if(barf & 0x0010) printf("Programming error.\n");
 
1038
                        if(barf & 0x0008) printf("Vpp Low error.\n");
 
1039
                        return(2);
 
1040
                }
 
1041
        }
 
1042
 
 
1043
        return (0);
 
1044
}
 
1045
 
 
1046
#else
 
1047
 
 
1048
static int write_short (flash_info_t *info, ulong dest, ushort data)
 
1049
{
 
1050
        vu_short *addr = (vu_short*)(info->start[0]);
 
1051
        ulong start,barf;
 
1052
        int flag;
 
1053
 
 
1054
        /* Check if Flash is (sufficiently) erased */
 
1055
        if ((*((vu_short *)dest) & data) != data) {
 
1056
                return (2);
 
1057
        }
 
1058
 
 
1059
        /* Disable interrupts which might cause a timeout here */
 
1060
        flag = disable_interrupts();
 
1061
 
 
1062
        if(info->flash_id < FLASH_AMD_COMP) {
 
1063
                /* AMD stuff */
 
1064
                addr[0x0555] = 0x00AA;
 
1065
                addr[0x02AA] = 0x0055;
 
1066
                addr[0x0555] = 0x00A0;
 
1067
        } else {
 
1068
                /* intel stuff */
 
1069
                *addr = 0x00D0;
 
1070
                *addr = 0x0040;
 
1071
        }
 
1072
        *((vu_short *)dest) = data;
 
1073
 
 
1074
        /* re-enable interrupts if necessary */
 
1075
        if (flag)
 
1076
                enable_interrupts();
 
1077
 
 
1078
        /* data polling for D7 */
 
1079
        start = get_timer (0);
 
1080
 
 
1081
        if(info->flash_id < FLASH_AMD_COMP) {
 
1082
                /* AMD stuff */
 
1083
                while ((*((vu_short *)dest) & 0x0080) != (data & 0x0080)) {
 
1084
                        if (get_timer(start) > CONFIG_SYS_FLASH_WRITE_TOUT) {
 
1085
                                return (1);
 
1086
                        }
 
1087
                }
 
1088
 
 
1089
        } else {
 
1090
                /* intel stuff */
 
1091
                while(!(addr[0] & 0x0080)){     /* wait for error or finish */
 
1092
                        if (get_timer(start) > CONFIG_SYS_FLASH_WRITE_TOUT) return (1);
 
1093
                }
 
1094
 
 
1095
                if( addr[0] & 0x003A) { /* check for error */
 
1096
                        barf = addr[0] & 0x003A;
 
1097
                        printf("\nFlash write error at address %lx\n",(unsigned long)dest);
 
1098
                        if(barf & 0x0002) printf("Block locked, not erased.\n");
 
1099
                        if(barf & 0x0010) printf("Programming error.\n");
 
1100
                        if(barf & 0x0008) printf("Vpp Low error.\n");
 
1101
                        return(2);
 
1102
                }
 
1103
                *addr = 0x00B0;
 
1104
                *addr = 0x0070;
 
1105
                while(!(addr[0] & 0x0080)){     /* wait for error or finish */
 
1106
                        if (get_timer(start) > CONFIG_SYS_FLASH_WRITE_TOUT) return (1);
 
1107
                }
 
1108
                *addr = 0x00FF;
 
1109
        }
 
1110
        return (0);
 
1111
}
 
1112
 
 
1113
#endif
 
1114
 
 
1115
/*-----------------------------------------------------------------------*/