3 * Sysgo Real-Time Solutions, GmbH <www.elinos.com>
4 * Alex Zuepke <azu@sysgo.de>
7 * 2N Telekomunikace, a.s. <www.2n.cz>
8 * Ladislav Michl <michl@2n.cz>
10 * See file CREDITS for list of people who contributed to this
13 * This program is free software; you can redistribute it and/or
14 * modify it under the terms of the GNU General Public License as
15 * published by the Free Software Foundation; either version 2 of
16 * the License, or (at your option) any later version.
18 * This program is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU General Public License for more details.
23 * You should have received a copy of the GNU General Public License
24 * along with this program; if not, write to the Free Software
25 * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
32 #if (PHYS_SDRAM_1_SIZE != SZ_32M)
36 #if (CONFIG_SYS_MAX_FLASH_BANKS > 1)
37 #error There is always only _one_ flash chip
40 flash_info_t flash_info[CONFIG_SYS_MAX_FLASH_BANKS];
42 #define CMD_READ_ARRAY 0x000000f0
43 #define CMD_UNLOCK1 0x000000aa
44 #define CMD_UNLOCK2 0x00000055
45 #define CMD_ERASE_SETUP 0x00000080
46 #define CMD_ERASE_CONFIRM 0x00000030
47 #define CMD_PROGRAM 0x000000a0
48 #define CMD_UNLOCK_BYPASS 0x00000020
50 #define MEM_FLASH_ADDR1 (*(volatile u16 *)(CONFIG_SYS_FLASH_BASE + (0x00000555 << 1)))
51 #define MEM_FLASH_ADDR2 (*(volatile u16 *)(CONFIG_SYS_FLASH_BASE + (0x000002aa << 1)))
53 #define BIT_ERASE_DONE 0x00000080
54 #define BIT_RDY_MASK 0x00000080
55 #define BIT_PROGRAM_ERROR 0x00000020
56 #define BIT_TIMEOUT 0x80000000 /* our flag */
58 /*-----------------------------------------------------------------------
61 ulong flash_init(void)
65 flash_info[0].flash_id = (AMD_MANUFACT & FLASH_VENDMASK) |
66 (AMD_ID_LV800B & FLASH_TYPEMASK);
67 flash_info[0].size = PHYS_FLASH_1_SIZE;
68 flash_info[0].sector_count = CONFIG_SYS_MAX_FLASH_SECT;
69 memset(flash_info[0].protect, 0, CONFIG_SYS_MAX_FLASH_SECT);
71 for (i = 0; i < flash_info[0].sector_count; i++) {
74 flash_info[0].start[0] = CONFIG_SYS_FLASH_BASE;
77 flash_info[0].start[1] = CONFIG_SYS_FLASH_BASE + 0x4000;
80 flash_info[0].start[2] = CONFIG_SYS_FLASH_BASE + 0x4000 +
84 flash_info[0].start[3] = CONFIG_SYS_FLASH_BASE + 0x4000 +
88 flash_info[0].start[4] = CONFIG_SYS_FLASH_BASE + 0x4000 +
92 flash_info[0].start[i] = flash_info[0].start[i-1] +
99 flash_protect(FLAG_PROTECT_SET,
101 LOADER1_OFFSET + LOADER_SIZE - 1, flash_info);
102 /* Protect crcek, env and r_env as well */
103 flash_protect(FLAG_PROTECT_SET, 0, 0x8000 - 1, flash_info);
105 return flash_info[0].size;
108 /*-----------------------------------------------------------------------
110 void flash_print_info(flash_info_t *info)
114 switch (info->flash_id & FLASH_VENDMASK) {
115 case (AMD_MANUFACT & FLASH_VENDMASK):
119 puts("Unknown vendor ");
123 switch (info->flash_id & FLASH_TYPEMASK) {
124 case (AMD_ID_LV800B & FLASH_TYPEMASK):
125 puts("AM29LV800BB (8Mb)\n");
128 puts("Unknown chip type\n");
132 printf(" Size: %ld MB in %d sectors\n",
133 info->size >> 20, info->sector_count);
135 puts(" Sector start addresses:");
136 for (i = 0; i < info->sector_count; i++) {
140 printf(" %08lX%s", info->start[i],
141 info->protect[i] ? " (RO)" : " ");
146 /*-----------------------------------------------------------------------
149 int flash_erase(flash_info_t *info, int s_first, int s_last)
155 /* first look for protection bits */
157 if (info->flash_id == FLASH_UNKNOWN)
158 return ERR_UNKNOWN_FLASH_TYPE;
160 if ((s_first < 0) || (s_first > s_last))
163 if ((info->flash_id & FLASH_VENDMASK) !=
164 (AMD_MANUFACT & FLASH_VENDMASK))
165 return ERR_UNKNOWN_FLASH_VENDOR;
168 for (sect = s_first; sect <= s_last; ++sect)
169 if (info->protect[sect])
173 printf("- Warning: %d protected sectors will not be erased!\n",
178 /* Start erase on unprotected sectors */
179 for (sect = s_first; sect <= s_last && !ctrlc (); sect++) {
180 if (info->protect[sect] == 0) { /* not protected */
181 vu_short *addr = (vu_short *) (info->start[sect]);
183 /* arm simple, non interrupt dependent timer */
184 reset_timer_masked();
186 MEM_FLASH_ADDR1 = CMD_UNLOCK1;
187 MEM_FLASH_ADDR2 = CMD_UNLOCK2;
188 MEM_FLASH_ADDR1 = CMD_ERASE_SETUP;
190 MEM_FLASH_ADDR1 = CMD_UNLOCK1;
191 MEM_FLASH_ADDR2 = CMD_UNLOCK2;
192 *addr = CMD_ERASE_CONFIRM;
194 /* wait until flash is ready */
199 if (get_timer_masked() > CONFIG_SYS_FLASH_ERASE_TOUT) {
200 MEM_FLASH_ADDR1 = CMD_READ_ARRAY;
205 if ((result & 0xfff) & BIT_ERASE_DONE)
208 if ((result & 0xffff) & BIT_PROGRAM_ERROR) {
214 MEM_FLASH_ADDR1 = CMD_READ_ARRAY;
223 /* allow flash to settle - wait 10 ms */
224 udelay_masked(10000);
229 /*-----------------------------------------------------------------------
230 * Copy memory to flash
233 static int write_hword(flash_info_t *info, ulong dest, ushort data)
235 vu_short *addr = (vu_short *) dest;
239 /* check if flash is (sufficiently) erased */
241 if ((result & data) != data)
242 return ERR_NOT_ERASED;
244 MEM_FLASH_ADDR1 = CMD_UNLOCK1;
245 MEM_FLASH_ADDR2 = CMD_UNLOCK2;
246 MEM_FLASH_ADDR1 = CMD_PROGRAM;
249 /* arm simple, non interrupt dependent timer */
250 reset_timer_masked();
252 /* wait until flash is ready */
257 if (get_timer_masked () > CONFIG_SYS_FLASH_ERASE_TOUT) {
262 if ((result & 0x80) == (data & 0x80))
265 if ((result & 0xffff) & BIT_PROGRAM_ERROR) {
268 if ((result & 0x80) != (data & 0x80))
273 *addr = CMD_READ_ARRAY;
281 /*-----------------------------------------------------------------------
282 * Copy memory to flash.
285 int write_buff(flash_info_t *info, uchar *src, ulong addr, ulong cnt)
292 wp = (addr & ~1); /* get lower word aligned address */
295 * handle unaligned start bytes
297 if ((l = addr - wp) != 0) {
299 for (i = 0, cp = wp; i < l; ++i, ++cp)
300 data = (data >> 8) | (*(uchar *) cp << 8);
301 for (; i < 2 && cnt > 0; ++i) {
302 data = (data >> 8) | (*src++ << 8);
306 for (; cnt == 0 && i < 2; ++i, ++cp)
307 data = (data >> 8) | (*(uchar *) cp << 8);
309 if ((rc = write_hword(info, wp, data)) != 0)
315 * handle word aligned part
318 data = *((vu_short *) src);
319 if ((rc = write_hword(info, wp, data)) != 0)
330 * handle unaligned tail bytes
333 for (i = 0, cp = wp; i < 2 && cnt > 0; ++i, ++cp) {
334 data = (data >> 8) | (*src++ << 8);
337 for (; i < 2; ++i, ++cp)
338 data = (data >> 8) | (*(uchar *) cp << 8);
340 return write_hword(info, wp, data);