1 /***************************************************************************
2 * Copyright (C) 2005, 2007 by Dominic Rath *
3 * Dominic.Rath@gmx.de *
5 * This program is free software; you can redistribute it and/or modify *
6 * it under the terms of the GNU General Public License as published by *
7 * the Free Software Foundation; either version 2 of the License, or *
8 * (at your option) any later version. *
10 * This program is distributed in the hope that it will be useful, *
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
13 * GNU General Public License for more details. *
15 * You should have received a copy of the GNU General Public License *
16 * along with this program; if not, write to the *
17 * Free Software Foundation, Inc., *
18 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
19 ***************************************************************************/
24 #include "replacements.h"
32 #include "algorithm.h"
33 #include "binarybuffer.h"
40 int cfi_register_commands(struct command_context_s
*cmd_ctx
);
41 int cfi_flash_bank_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
, struct flash_bank_s
*bank
);
42 int cfi_erase(struct flash_bank_s
*bank
, int first
, int last
);
43 int cfi_protect(struct flash_bank_s
*bank
, int set
, int first
, int last
);
44 int cfi_write(struct flash_bank_s
*bank
, u8
*buffer
, u32 offset
, u32 count
);
45 int cfi_probe(struct flash_bank_s
*bank
);
46 int cfi_erase_check(struct flash_bank_s
*bank
);
47 int cfi_protect_check(struct flash_bank_s
*bank
);
48 int cfi_info(struct flash_bank_s
*bank
, char *buf
, int buf_size
);
50 int cfi_handle_part_id_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
);
52 #define CFI_MAX_BUS_WIDTH 4
53 #define CFI_MAX_CHIP_WIDTH 4
55 flash_driver_t cfi_flash
=
58 .register_commands
= cfi_register_commands
,
59 .flash_bank_command
= cfi_flash_bank_command
,
61 .protect
= cfi_protect
,
64 .erase_check
= cfi_erase_check
,
65 .protect_check
= cfi_protect_check
,
69 cfi_unlock_addresses_t cfi_unlock_addresses
[] =
71 [CFI_UNLOCK_555_2AA
] = { .unlock1
= 0x555, .unlock2
= 0x2aa },
72 [CFI_UNLOCK_5555_2AAA
] = { .unlock1
= 0x5555, .unlock2
= 0x2aaa },
75 /* CFI fixups foward declarations */
76 void cfi_fixup_non_cfi(flash_bank_t
*flash
, void *param
);
77 void cfi_fixup_0002_erase_regions(flash_bank_t
*flash
, void *param
);
78 void cfi_fixup_0002_unlock_addresses(flash_bank_t
*flash
, void *param
);
79 void cfi_fixup_atmel_reversed_erase_regions(flash_bank_t
*flash
, void *param
);
81 /* fixup after identifying JEDEC manufactuer and ID */
82 cfi_fixup_t cfi_jedec_fixups
[] = {
83 {CFI_MFR_SST
, 0x00D4, cfi_fixup_non_cfi
, NULL
},
84 {CFI_MFR_SST
, 0x00D5, cfi_fixup_non_cfi
, NULL
},
85 {CFI_MFR_SST
, 0x00D6, cfi_fixup_non_cfi
, NULL
},
86 {CFI_MFR_SST
, 0x00D7, cfi_fixup_non_cfi
, NULL
},
87 {CFI_MFR_ST
, 0x00D5, cfi_fixup_non_cfi
, NULL
},
88 {CFI_MFR_ST
, 0x00D6, cfi_fixup_non_cfi
, NULL
},
89 {CFI_MFR_AMD
, 0x2223, cfi_fixup_non_cfi
, NULL
},
90 {CFI_MFR_AMD
, 0x22ab, cfi_fixup_non_cfi
, NULL
},
94 /* fixup after reading cmdset 0002 primary query table */
95 cfi_fixup_t cfi_0002_fixups
[] = {
96 {CFI_MFR_SST
, 0x00D4, cfi_fixup_0002_unlock_addresses
, &cfi_unlock_addresses
[CFI_UNLOCK_5555_2AAA
]},
97 {CFI_MFR_SST
, 0x00D5, cfi_fixup_0002_unlock_addresses
, &cfi_unlock_addresses
[CFI_UNLOCK_5555_2AAA
]},
98 {CFI_MFR_SST
, 0x00D6, cfi_fixup_0002_unlock_addresses
, &cfi_unlock_addresses
[CFI_UNLOCK_5555_2AAA
]},
99 {CFI_MFR_SST
, 0x00D7, cfi_fixup_0002_unlock_addresses
, &cfi_unlock_addresses
[CFI_UNLOCK_5555_2AAA
]},
100 {CFI_MFR_ATMEL
, 0x00C8, cfi_fixup_atmel_reversed_erase_regions
, NULL
},
101 {CFI_MFR_ANY
, CFI_ID_ANY
, cfi_fixup_0002_erase_regions
, NULL
},
105 /* fixup after reading cmdset 0001 primary query table */
106 cfi_fixup_t cfi_0001_fixups
[] = {
110 void cfi_fixup(flash_bank_t
*bank
, cfi_fixup_t
*fixups
)
112 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
115 for (f
= fixups
; f
->fixup
; f
++)
117 if (((f
->mfr
== CFI_MFR_ANY
) || (f
->mfr
== cfi_info
->manufacturer
)) &&
118 ((f
->id
== CFI_ID_ANY
) || (f
->id
== cfi_info
->device_id
)))
120 f
->fixup(bank
, f
->param
);
125 inline u32
flash_address(flash_bank_t
*bank
, int sector
, u32 offset
)
127 /* while the sector list isn't built, only accesses to sector 0 work */
129 return bank
->base
+ offset
* bank
->bus_width
;
134 ERROR("BUG: sector list not yet built");
137 return bank
->base
+ bank
->sectors
[sector
].offset
+ offset
* bank
->bus_width
;
142 void cfi_command(flash_bank_t
*bank
, u8 cmd
, u8
*cmd_buf
)
146 /* clear whole buffer, to ensure bits that exceed the bus_width
149 for (i
= 0; i
< CFI_MAX_BUS_WIDTH
; i
++)
152 if (bank
->target
->endianness
== TARGET_LITTLE_ENDIAN
)
154 for (i
= bank
->bus_width
; i
> 0; i
--)
156 *cmd_buf
++ = (i
& (bank
->chip_width
- 1)) ? 0x0 : cmd
;
161 for (i
= 1; i
<= bank
->bus_width
; i
++)
163 *cmd_buf
++ = (i
& (bank
->chip_width
- 1)) ? 0x0 : cmd
;
168 /* read unsigned 8-bit value from the bank
169 * flash banks are expected to be made of similar chips
170 * the query result should be the same for all
172 u8
cfi_query_u8(flash_bank_t
*bank
, int sector
, u32 offset
)
174 target_t
*target
= bank
->target
;
175 u8 data
[CFI_MAX_BUS_WIDTH
];
177 target
->type
->read_memory(target
, flash_address(bank
, sector
, offset
), bank
->bus_width
, 1, data
);
179 if (bank
->target
->endianness
== TARGET_LITTLE_ENDIAN
)
182 return data
[bank
->bus_width
- 1];
185 /* read unsigned 8-bit value from the bank
186 * in case of a bank made of multiple chips,
187 * the individual values are ORed
189 u8
cfi_get_u8(flash_bank_t
*bank
, int sector
, u32 offset
)
191 target_t
*target
= bank
->target
;
192 u8 data
[CFI_MAX_BUS_WIDTH
];
195 target
->type
->read_memory(target
, flash_address(bank
, sector
, offset
), bank
->bus_width
, 1, data
);
197 if (bank
->target
->endianness
== TARGET_LITTLE_ENDIAN
)
199 for (i
= 0; i
< bank
->bus_width
/ bank
->chip_width
; i
++)
207 for (i
= 0; i
< bank
->bus_width
/ bank
->chip_width
; i
++)
208 value
|= data
[bank
->bus_width
- 1 - i
];
214 u16
cfi_query_u16(flash_bank_t
*bank
, int sector
, u32 offset
)
216 target_t
*target
= bank
->target
;
217 u8 data
[CFI_MAX_BUS_WIDTH
* 2];
219 target
->type
->read_memory(target
, flash_address(bank
, sector
, offset
), bank
->bus_width
, 2, data
);
221 if (bank
->target
->endianness
== TARGET_LITTLE_ENDIAN
)
222 return data
[0] | data
[bank
->bus_width
] << 8;
224 return data
[bank
->bus_width
- 1] | data
[(2 * bank
->bus_width
) - 1] << 8;
227 u32
cfi_query_u32(flash_bank_t
*bank
, int sector
, u32 offset
)
229 target_t
*target
= bank
->target
;
230 u8 data
[CFI_MAX_BUS_WIDTH
* 4];
232 target
->type
->read_memory(target
, flash_address(bank
, sector
, offset
), bank
->bus_width
, 4, data
);
234 if (bank
->target
->endianness
== TARGET_LITTLE_ENDIAN
)
235 return data
[0] | data
[bank
->bus_width
] << 8 | data
[bank
->bus_width
* 2] << 16 | data
[bank
->bus_width
* 3] << 24;
237 return data
[bank
->bus_width
- 1] | data
[(2* bank
->bus_width
) - 1] << 8 |
238 data
[(3 * bank
->bus_width
) - 1] << 16 | data
[(4 * bank
->bus_width
) - 1] << 24;
241 void cfi_intel_clear_status_register(flash_bank_t
*bank
)
243 target_t
*target
= bank
->target
;
246 if (target
->state
!= TARGET_HALTED
)
248 ERROR("BUG: attempted to clear status register while target wasn't halted");
252 cfi_command(bank
, 0x50, command
);
253 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
256 u8
cfi_intel_wait_status_busy(flash_bank_t
*bank
, int timeout
)
260 while ((!((status
= cfi_get_u8(bank
, 0, 0x0)) & 0x80)) && (timeout
-- > 0))
262 DEBUG("status: 0x%x", status
);
266 /* mask out bit 0 (reserved) */
267 status
= status
& 0xfe;
269 DEBUG("status: 0x%x", status
);
271 if ((status
& 0x80) != 0x80)
273 ERROR("timeout while waiting for WSM to become ready");
275 else if (status
!= 0x80)
277 ERROR("status register: 0x%x", status
);
279 ERROR("Block Lock-Bit Detected, Operation Abort");
281 ERROR("Program suspended");
283 ERROR("Low Programming Voltage Detected, Operation Aborted");
285 ERROR("Program Error / Error in Setting Lock-Bit");
287 ERROR("Error in Block Erasure or Clear Lock-Bits");
289 ERROR("Block Erase Suspended");
291 cfi_intel_clear_status_register(bank
);
297 int cfi_spansion_wait_status_busy(flash_bank_t
*bank
, int timeout
)
299 u8 status
, oldstatus
;
301 oldstatus
= cfi_get_u8(bank
, 0, 0x0);
304 status
= cfi_get_u8(bank
, 0, 0x0);
305 if ((status
^ oldstatus
) & 0x40) {
307 oldstatus
= cfi_get_u8(bank
, 0, 0x0);
308 status
= cfi_get_u8(bank
, 0, 0x0);
309 if ((status
^ oldstatus
) & 0x40) {
310 ERROR("dq5 timeout, status: 0x%x", status
);
311 return(ERROR_FLASH_OPERATION_FAILED
);
313 DEBUG("status: 0x%x", status
);
318 DEBUG("status: 0x%x", status
);
324 } while (timeout
-- > 0);
326 ERROR("timeout, status: 0x%x", status
);
328 return(ERROR_FLASH_BUSY
);
331 int cfi_read_intel_pri_ext(flash_bank_t
*bank
)
333 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
334 cfi_intel_pri_ext_t
*pri_ext
= malloc(sizeof(cfi_intel_pri_ext_t
));
335 target_t
*target
= bank
->target
;
338 cfi_info
->pri_ext
= pri_ext
;
340 pri_ext
->pri
[0] = cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 0);
341 pri_ext
->pri
[1] = cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 1);
342 pri_ext
->pri
[2] = cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 2);
344 if ((pri_ext
->pri
[0] != 'P') || (pri_ext
->pri
[1] != 'R') || (pri_ext
->pri
[2] != 'I'))
346 cfi_command(bank
, 0xf0, command
);
347 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
348 cfi_command(bank
, 0xff, command
);
349 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
350 return ERROR_FLASH_BANK_INVALID
;
353 pri_ext
->major_version
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 3);
354 pri_ext
->minor_version
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 4);
356 DEBUG("pri: '%c%c%c', version: %c.%c", pri_ext
->pri
[0], pri_ext
->pri
[1], pri_ext
->pri
[2], pri_ext
->major_version
, pri_ext
->minor_version
);
358 pri_ext
->feature_support
= cfi_query_u32(bank
, 0, cfi_info
->pri_addr
+ 5);
359 pri_ext
->suspend_cmd_support
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 9);
360 pri_ext
->blk_status_reg_mask
= cfi_query_u16(bank
, 0, cfi_info
->pri_addr
+ 0xa);
362 DEBUG("feature_support: 0x%x, suspend_cmd_support: 0x%x, blk_status_reg_mask: 0x%x", pri_ext
->feature_support
, pri_ext
->suspend_cmd_support
, pri_ext
->blk_status_reg_mask
);
364 pri_ext
->vcc_optimal
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 0xc);
365 pri_ext
->vpp_optimal
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 0xd);
367 DEBUG("Vcc opt: %1.1x.%1.1x, Vpp opt: %1.1x.%1.1x",
368 (pri_ext
->vcc_optimal
& 0xf0) >> 4, pri_ext
->vcc_optimal
& 0x0f,
369 (pri_ext
->vpp_optimal
& 0xf0) >> 4, pri_ext
->vpp_optimal
& 0x0f);
371 pri_ext
->num_protection_fields
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 0xe);
372 if (pri_ext
->num_protection_fields
!= 1)
374 WARNING("expected one protection register field, but found %i", pri_ext
->num_protection_fields
);
377 pri_ext
->prot_reg_addr
= cfi_query_u16(bank
, 0, cfi_info
->pri_addr
+ 0xf);
378 pri_ext
->fact_prot_reg_size
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 0x11);
379 pri_ext
->user_prot_reg_size
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 0x12);
381 DEBUG("protection_fields: %i, prot_reg_addr: 0x%x, factory pre-programmed: %i, user programmable: %i", pri_ext
->num_protection_fields
, pri_ext
->prot_reg_addr
, 1 << pri_ext
->fact_prot_reg_size
, 1 << pri_ext
->user_prot_reg_size
);
386 int cfi_read_spansion_pri_ext(flash_bank_t
*bank
)
388 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
389 cfi_spansion_pri_ext_t
*pri_ext
= malloc(sizeof(cfi_spansion_pri_ext_t
));
390 target_t
*target
= bank
->target
;
393 cfi_info
->pri_ext
= pri_ext
;
395 pri_ext
->pri
[0] = cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 0);
396 pri_ext
->pri
[1] = cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 1);
397 pri_ext
->pri
[2] = cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 2);
399 if ((pri_ext
->pri
[0] != 'P') || (pri_ext
->pri
[1] != 'R') || (pri_ext
->pri
[2] != 'I'))
401 cfi_command(bank
, 0xf0, command
);
402 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
403 return ERROR_FLASH_BANK_INVALID
;
406 pri_ext
->major_version
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 3);
407 pri_ext
->minor_version
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 4);
409 DEBUG("pri: '%c%c%c', version: %c.%c", pri_ext
->pri
[0], pri_ext
->pri
[1], pri_ext
->pri
[2], pri_ext
->major_version
, pri_ext
->minor_version
);
411 pri_ext
->SiliconRevision
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 5);
412 pri_ext
->EraseSuspend
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 6);
413 pri_ext
->BlkProt
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 7);
414 pri_ext
->TmpBlkUnprotect
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 8);
415 pri_ext
->BlkProtUnprot
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 9);
416 pri_ext
->SimultaneousOps
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 10);
417 pri_ext
->BurstMode
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 11);
418 pri_ext
->PageMode
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 12);
419 pri_ext
->VppMin
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 13);
420 pri_ext
->VppMax
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 14);
421 pri_ext
->TopBottom
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 15);
423 DEBUG("Silicon Revision: 0x%x, Erase Suspend: 0x%x, Block protect: 0x%x", pri_ext
->SiliconRevision
,
424 pri_ext
->EraseSuspend
, pri_ext
->BlkProt
);
426 DEBUG("Temporary Unprotect: 0x%x, Block Protect Scheme: 0x%x, Simultaneous Ops: 0x%x", pri_ext
->TmpBlkUnprotect
,
427 pri_ext
->BlkProtUnprot
, pri_ext
->SimultaneousOps
);
429 DEBUG("Burst Mode: 0x%x, Page Mode: 0x%x, ", pri_ext
->BurstMode
, pri_ext
->PageMode
);
432 DEBUG("Vpp min: %2.2d.%1.1d, Vpp max: %2.2d.%1.1x",
433 (pri_ext
->VppMin
& 0xf0) >> 4, pri_ext
->VppMin
& 0x0f,
434 (pri_ext
->VppMax
& 0xf0) >> 4, pri_ext
->VppMax
& 0x0f);
436 DEBUG("WP# protection 0x%x", pri_ext
->TopBottom
);
438 /* default values for implementation specific workarounds */
439 pri_ext
->_unlock1
= cfi_unlock_addresses
[CFI_UNLOCK_555_2AA
].unlock1
;
440 pri_ext
->_unlock2
= cfi_unlock_addresses
[CFI_UNLOCK_555_2AA
].unlock2
;
441 pri_ext
->_reversed_geometry
= 0;
446 int cfi_read_atmel_pri_ext(flash_bank_t
*bank
)
448 cfi_atmel_pri_ext_t atmel_pri_ext
;
449 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
450 cfi_spansion_pri_ext_t
*pri_ext
= malloc(sizeof(cfi_spansion_pri_ext_t
));
451 target_t
*target
= bank
->target
;
454 /* ATMEL devices use the same CFI primary command set (0x2) as AMD/Spansion,
455 * but a different primary extended query table.
456 * We read the atmel table, and prepare a valid AMD/Spansion query table.
459 memset(pri_ext
, 0, sizeof(cfi_spansion_pri_ext_t
));
461 cfi_info
->pri_ext
= pri_ext
;
463 atmel_pri_ext
.pri
[0] = cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 0);
464 atmel_pri_ext
.pri
[1] = cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 1);
465 atmel_pri_ext
.pri
[2] = cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 2);
467 if ((atmel_pri_ext
.pri
[0] != 'P') || (atmel_pri_ext
.pri
[1] != 'R') || (atmel_pri_ext
.pri
[2] != 'I'))
469 cfi_command(bank
, 0xf0, command
);
470 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
471 return ERROR_FLASH_BANK_INVALID
;
474 pri_ext
->pri
[0] = atmel_pri_ext
.pri
[0];
475 pri_ext
->pri
[1] = atmel_pri_ext
.pri
[1];
476 pri_ext
->pri
[2] = atmel_pri_ext
.pri
[2];
478 atmel_pri_ext
.major_version
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 3);
479 atmel_pri_ext
.minor_version
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 4);
481 DEBUG("pri: '%c%c%c', version: %c.%c", atmel_pri_ext
.pri
[0], atmel_pri_ext
.pri
[1], atmel_pri_ext
.pri
[2], atmel_pri_ext
.major_version
, atmel_pri_ext
.minor_version
);
483 pri_ext
->major_version
= atmel_pri_ext
.major_version
;
484 pri_ext
->minor_version
= atmel_pri_ext
.minor_version
;
486 atmel_pri_ext
.features
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 5);
487 atmel_pri_ext
.bottom_boot
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 6);
488 atmel_pri_ext
.burst_mode
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 7);
489 atmel_pri_ext
.page_mode
= cfi_query_u8(bank
, 0, cfi_info
->pri_addr
+ 8);
491 DEBUG("features: 0x%2.2x, bottom_boot: 0x%2.2x, burst_mode: 0x%2.2x, page_mode: 0x%2.2x",
492 atmel_pri_ext
.features
, atmel_pri_ext
.bottom_boot
, atmel_pri_ext
.burst_mode
, atmel_pri_ext
.page_mode
);
494 if (atmel_pri_ext
.features
& 0x02)
495 pri_ext
->EraseSuspend
= 2;
497 if (atmel_pri_ext
.bottom_boot
)
498 pri_ext
->TopBottom
= 2;
500 pri_ext
->TopBottom
= 3;
505 int cfi_read_0002_pri_ext(flash_bank_t
*bank
)
507 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
509 if (cfi_info
->manufacturer
== CFI_MFR_ATMEL
)
511 return cfi_read_atmel_pri_ext(bank
);
515 return cfi_read_spansion_pri_ext(bank
);
519 int cfi_spansion_info(struct flash_bank_s
*bank
, char *buf
, int buf_size
)
522 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
523 cfi_spansion_pri_ext_t
*pri_ext
= cfi_info
->pri_ext
;
525 printed
= snprintf(buf
, buf_size
, "\nSpansion primary algorithm extend information:\n");
529 printed
= snprintf(buf
, buf_size
, "pri: '%c%c%c', version: %c.%c\n", pri_ext
->pri
[0],
530 pri_ext
->pri
[1], pri_ext
->pri
[2],
531 pri_ext
->major_version
, pri_ext
->minor_version
);
535 printed
= snprintf(buf
, buf_size
, "Silicon Rev.: 0x%x, Address Sensitive unlock: 0x%x\n",
536 (pri_ext
->SiliconRevision
) >> 2,
537 (pri_ext
->SiliconRevision
) & 0x03);
541 printed
= snprintf(buf
, buf_size
, "Erase Suspend: 0x%x, Sector Protect: 0x%x\n",
542 pri_ext
->EraseSuspend
,
547 printed
= snprintf(buf
, buf_size
, "VppMin: %2.2d.%1.1x, VppMax: %2.2d.%1.1x\n",
548 (pri_ext
->VppMin
& 0xf0) >> 4, pri_ext
->VppMin
& 0x0f,
549 (pri_ext
->VppMax
& 0xf0) >> 4, pri_ext
->VppMax
& 0x0f);
554 int cfi_intel_info(struct flash_bank_s
*bank
, char *buf
, int buf_size
)
557 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
558 cfi_intel_pri_ext_t
*pri_ext
= cfi_info
->pri_ext
;
560 printed
= snprintf(buf
, buf_size
, "\nintel primary algorithm extend information:\n");
564 printed
= snprintf(buf
, buf_size
, "pri: '%c%c%c', version: %c.%c\n", pri_ext
->pri
[0], pri_ext
->pri
[1], pri_ext
->pri
[2], pri_ext
->major_version
, pri_ext
->minor_version
);
568 printed
= snprintf(buf
, buf_size
, "feature_support: 0x%x, suspend_cmd_support: 0x%x, blk_status_reg_mask: 0x%x\n", pri_ext
->feature_support
, pri_ext
->suspend_cmd_support
, pri_ext
->blk_status_reg_mask
);
572 printed
= snprintf(buf
, buf_size
, "Vcc opt: %1.1x.%1.1x, Vpp opt: %1.1x.%1.1x\n",
573 (pri_ext
->vcc_optimal
& 0xf0) >> 4, pri_ext
->vcc_optimal
& 0x0f,
574 (pri_ext
->vpp_optimal
& 0xf0) >> 4, pri_ext
->vpp_optimal
& 0x0f);
578 printed
= snprintf(buf
, buf_size
, "protection_fields: %i, prot_reg_addr: 0x%x, factory pre-programmed: %i, user programmable: %i\n", pri_ext
->num_protection_fields
, pri_ext
->prot_reg_addr
, 1 << pri_ext
->fact_prot_reg_size
, 1 << pri_ext
->user_prot_reg_size
);
583 int cfi_register_commands(struct command_context_s
*cmd_ctx
)
585 /*command_t *cfi_cmd = */register_command(cmd_ctx
, NULL
, "cfi", NULL
, COMMAND_ANY
, NULL
);
587 register_command(cmd_ctx, cfi_cmd, "part_id", cfi_handle_part_id_command, COMMAND_EXEC,
588 "print part id of cfi flash bank <num>");
593 /* flash_bank cfi <base> <size> <chip_width> <bus_width> <target#> [options]
595 int cfi_flash_bank_command(struct command_context_s
*cmd_ctx
, char *cmd
, char **args
, int argc
, struct flash_bank_s
*bank
)
597 cfi_flash_bank_t
*cfi_info
;
602 WARNING("incomplete flash_bank cfi configuration");
603 return ERROR_FLASH_BANK_INVALID
;
606 if ((strtoul(args
[4], NULL
, 0) > CFI_MAX_CHIP_WIDTH
)
607 || (strtoul(args
[3], NULL
, 0) > CFI_MAX_BUS_WIDTH
))
609 ERROR("chip and bus width have to specified in byte");
610 return ERROR_FLASH_BANK_INVALID
;
613 cfi_info
= malloc(sizeof(cfi_flash_bank_t
));
614 bank
->driver_priv
= cfi_info
;
616 cfi_info
->x16_as_x8
= 0;
617 cfi_info
->jedec_probe
= 0;
618 cfi_info
->not_cfi
= 0;
620 for (i
= 6; i
< argc
; i
++)
622 if (strcmp(args
[i
], "x16_as_x8") == 0)
624 cfi_info
->x16_as_x8
= 1;
626 else if (strcmp(args
[i
], "jedec_probe") == 0)
628 cfi_info
->jedec_probe
= 1;
632 cfi_info
->write_algorithm
= NULL
;
634 /* bank wasn't probed yet */
635 cfi_info
->qry
[0] = -1;
640 int cfi_intel_erase(struct flash_bank_s
*bank
, int first
, int last
)
642 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
643 target_t
*target
= bank
->target
;
647 cfi_intel_clear_status_register(bank
);
649 for (i
= first
; i
<= last
; i
++)
651 cfi_command(bank
, 0x20, command
);
652 target
->type
->write_memory(target
, flash_address(bank
, i
, 0x0), bank
->bus_width
, 1, command
);
654 cfi_command(bank
, 0xd0, command
);
655 target
->type
->write_memory(target
, flash_address(bank
, i
, 0x0), bank
->bus_width
, 1, command
);
657 if (cfi_intel_wait_status_busy(bank
, 1000 * (1 << cfi_info
->block_erase_timeout_typ
)) == 0x80)
658 bank
->sectors
[i
].is_erased
= 1;
661 cfi_command(bank
, 0xff, command
);
662 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
664 ERROR("couldn't erase block %i of flash bank at base 0x%x", i
, bank
->base
);
665 return ERROR_FLASH_OPERATION_FAILED
;
669 cfi_command(bank
, 0xff, command
);
670 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
675 int cfi_spansion_erase(struct flash_bank_s
*bank
, int first
, int last
)
677 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
678 cfi_spansion_pri_ext_t
*pri_ext
= cfi_info
->pri_ext
;
679 target_t
*target
= bank
->target
;
683 for (i
= first
; i
<= last
; i
++)
685 cfi_command(bank
, 0xaa, command
);
686 target
->type
->write_memory(target
, flash_address(bank
, 0, pri_ext
->_unlock1
), bank
->bus_width
, 1, command
);
688 cfi_command(bank
, 0x55, command
);
689 target
->type
->write_memory(target
, flash_address(bank
, 0, pri_ext
->_unlock2
), bank
->bus_width
, 1, command
);
691 cfi_command(bank
, 0x80, command
);
692 target
->type
->write_memory(target
, flash_address(bank
, 0, pri_ext
->_unlock1
), bank
->bus_width
, 1, command
);
694 cfi_command(bank
, 0xaa, command
);
695 target
->type
->write_memory(target
, flash_address(bank
, 0, pri_ext
->_unlock1
), bank
->bus_width
, 1, command
);
697 cfi_command(bank
, 0x55, command
);
698 target
->type
->write_memory(target
, flash_address(bank
, 0, pri_ext
->_unlock2
), bank
->bus_width
, 1, command
);
700 cfi_command(bank
, 0x30, command
);
701 target
->type
->write_memory(target
, flash_address(bank
, i
, 0x0), bank
->bus_width
, 1, command
);
703 if (cfi_spansion_wait_status_busy(bank
, 1000 * (1 << cfi_info
->block_erase_timeout_typ
)) == ERROR_OK
)
704 bank
->sectors
[i
].is_erased
= 1;
707 cfi_command(bank
, 0xf0, command
);
708 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
710 ERROR("couldn't erase block %i of flash bank at base 0x%x", i
, bank
->base
);
711 return ERROR_FLASH_OPERATION_FAILED
;
715 cfi_command(bank
, 0xf0, command
);
716 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
721 int cfi_erase(struct flash_bank_s
*bank
, int first
, int last
)
723 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
725 if (bank
->target
->state
!= TARGET_HALTED
)
727 return ERROR_TARGET_NOT_HALTED
;
730 if ((first
< 0) || (last
< first
) || (last
>= bank
->num_sectors
))
732 return ERROR_FLASH_SECTOR_INVALID
;
735 if (cfi_info
->qry
[0] != 'Q')
736 return ERROR_FLASH_BANK_NOT_PROBED
;
738 switch(cfi_info
->pri_id
)
742 return cfi_intel_erase(bank
, first
, last
);
745 return cfi_spansion_erase(bank
, first
, last
);
748 ERROR("cfi primary command set %i unsupported", cfi_info
->pri_id
);
755 int cfi_intel_protect(struct flash_bank_s
*bank
, int set
, int first
, int last
)
757 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
758 cfi_intel_pri_ext_t
*pri_ext
= cfi_info
->pri_ext
;
759 target_t
*target
= bank
->target
;
764 /* if the device supports neither legacy lock/unlock (bit 3) nor
765 * instant individual block locking (bit 5).
767 if (!(pri_ext
->feature_support
& 0x28))
768 return ERROR_FLASH_OPERATION_FAILED
;
770 cfi_intel_clear_status_register(bank
);
772 for (i
= first
; i
<= last
; i
++)
774 cfi_command(bank
, 0x60, command
);
775 DEBUG("address: 0x%4.4x, command: 0x%4.4x", flash_address(bank
, i
, 0x0), target_buffer_get_u32(target
, command
));
776 target
->type
->write_memory(target
, flash_address(bank
, i
, 0x0), bank
->bus_width
, 1, command
);
779 cfi_command(bank
, 0x01, command
);
780 DEBUG("address: 0x%4.4x, command: 0x%4.4x", flash_address(bank
, i
, 0x0), target_buffer_get_u32(target
, command
));
781 target
->type
->write_memory(target
, flash_address(bank
, i
, 0x0), bank
->bus_width
, 1, command
);
782 bank
->sectors
[i
].is_protected
= 1;
786 cfi_command(bank
, 0xd0, command
);
787 DEBUG("address: 0x%4.4x, command: 0x%4.4x", flash_address(bank
, i
, 0x0), target_buffer_get_u32(target
, command
));
788 target
->type
->write_memory(target
, flash_address(bank
, i
, 0x0), bank
->bus_width
, 1, command
);
789 bank
->sectors
[i
].is_protected
= 0;
792 /* instant individual block locking doesn't require reading of the status register */
793 if (!(pri_ext
->feature_support
& 0x20))
795 /* Clear lock bits operation may take up to 1.4s */
796 cfi_intel_wait_status_busy(bank
, 1400);
801 /* read block lock bit, to verify status */
802 cfi_command(bank
, 0x90, command
);
803 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x55), bank
->bus_width
, 1, command
);
804 block_status
= cfi_get_u8(bank
, i
, 0x2);
806 if ((block_status
& 0x1) != set
)
808 ERROR("couldn't change block lock status (set = %i, block_status = 0x%2.2x)", set
, block_status
);
809 cfi_command(bank
, 0x70, command
);
810 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x55), bank
->bus_width
, 1, command
);
811 cfi_intel_wait_status_busy(bank
, 10);
814 return ERROR_FLASH_OPERATION_FAILED
;
824 /* if the device doesn't support individual block lock bits set/clear,
825 * all blocks have been unlocked in parallel, so we set those that should be protected
827 if ((!set
) && (!(pri_ext
->feature_support
& 0x20)))
829 for (i
= 0; i
< bank
->num_sectors
; i
++)
831 cfi_intel_clear_status_register(bank
);
832 cfi_command(bank
, 0x60, command
);
833 target
->type
->write_memory(target
, flash_address(bank
, i
, 0x0), bank
->bus_width
, 1, command
);
834 if (bank
->sectors
[i
].is_protected
== 1)
836 cfi_command(bank
, 0x01, command
);
837 target
->type
->write_memory(target
, flash_address(bank
, i
, 0x0), bank
->bus_width
, 1, command
);
840 cfi_intel_wait_status_busy(bank
, 100);
844 cfi_command(bank
, 0xff, command
);
845 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
850 int cfi_protect(struct flash_bank_s
*bank
, int set
, int first
, int last
)
852 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
854 if (bank
->target
->state
!= TARGET_HALTED
)
856 return ERROR_TARGET_NOT_HALTED
;
859 if ((first
< 0) || (last
< first
) || (last
>= bank
->num_sectors
))
861 return ERROR_FLASH_SECTOR_INVALID
;
864 if (cfi_info
->qry
[0] != 'Q')
865 return ERROR_FLASH_BANK_NOT_PROBED
;
867 switch(cfi_info
->pri_id
)
871 cfi_intel_protect(bank
, set
, first
, last
);
874 ERROR("cfi primary command set %i unsupported", cfi_info
->pri_id
);
881 void cfi_add_byte(struct flash_bank_s
*bank
, u8
*word
, u8 byte
)
883 target_t
*target
= bank
->target
;
887 if (target
->endianness
== TARGET_LITTLE_ENDIAN
)
890 for (i
= 0; i
< bank
->bus_width
- 1; i
++)
891 word
[i
] = word
[i
+ 1];
892 word
[bank
->bus_width
- 1] = byte
;
897 for (i
= bank
->bus_width
- 1; i
> 0; i
--)
898 word
[i
] = word
[i
- 1];
903 int cfi_intel_write_block(struct flash_bank_s
*bank
, u8
*buffer
, u32 address
, u32 count
)
905 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
906 target_t
*target
= bank
->target
;
907 reg_param_t reg_params
[7];
908 armv4_5_algorithm_t armv4_5_info
;
909 working_area_t
*source
;
910 u32 buffer_size
= 32768;
911 u8 write_command_buf
[CFI_MAX_BUS_WIDTH
];
912 u8 busy_pattern_buf
[CFI_MAX_BUS_WIDTH
];
913 u8 error_pattern_buf
[CFI_MAX_BUS_WIDTH
];
914 u32 write_command_val
, busy_pattern_val
, error_pattern_val
;
917 /* algorithm register usage:
918 * r0: source address (in RAM)
919 * r1: target address (in Flash)
921 * r3: flash write command
922 * r4: status byte (returned to host)
923 * r5: busy test pattern
924 * r6: error test pattern
927 static const u32 word_32_code
[] = {
928 0xe4904004, /* loop: ldr r4, [r0], #4 */
929 0xe5813000, /* str r3, [r1] */
930 0xe5814000, /* str r4, [r1] */
931 0xe5914000, /* busy: ldr r4, [r1] */
932 0xe0047005, /* and r7, r4, r5 */
933 0xe1570005, /* cmp r7, r5 */
934 0x1afffffb, /* bne busy */
935 0xe1140006, /* tst r4, r6 */
936 0x1a000003, /* bne done */
937 0xe2522001, /* subs r2, r2, #1 */
938 0x0a000001, /* beq done */
939 0xe2811004, /* add r1, r1 #4 */
940 0xeafffff2, /* b loop */
941 0xeafffffe, /* done: b -2 */
944 static const u32 word_16_code
[] = {
945 0xe0d040b2, /* loop: ldrh r4, [r0], #2 */
946 0xe1c130b0, /* strh r3, [r1] */
947 0xe1c140b0, /* strh r4, [r1] */
948 0xe1d140b0, /* busy ldrh r4, [r1] */
949 0xe0047005, /* and r7, r4, r5 */
950 0xe1570005, /* cmp r7, r5 */
951 0x1afffffb, /* bne busy */
952 0xe1140006, /* tst r4, r6 */
953 0x1a000003, /* bne done */
954 0xe2522001, /* subs r2, r2, #1 */
955 0x0a000001, /* beq done */
956 0xe2811002, /* add r1, r1 #2 */
957 0xeafffff2, /* b loop */
958 0xeafffffe, /* done: b -2 */
961 static const u32 word_8_code
[] = {
962 0xe4d04001, /* loop: ldrb r4, [r0], #1 */
963 0xe5c13000, /* strb r3, [r1] */
964 0xe5c14000, /* strb r4, [r1] */
965 0xe5d14000, /* busy ldrb r4, [r1] */
966 0xe0047005, /* and r7, r4, r5 */
967 0xe1570005, /* cmp r7, r5 */
968 0x1afffffb, /* bne busy */
969 0xe1140006, /* tst r4, r6 */
970 0x1a000003, /* bne done */
971 0xe2522001, /* subs r2, r2, #1 */
972 0x0a000001, /* beq done */
973 0xe2811001, /* add r1, r1 #1 */
974 0xeafffff2, /* b loop */
975 0xeafffffe, /* done: b -2 */
978 cfi_intel_clear_status_register(bank
);
980 armv4_5_info
.common_magic
= ARMV4_5_COMMON_MAGIC
;
981 armv4_5_info
.core_mode
= ARMV4_5_MODE_SVC
;
982 armv4_5_info
.core_state
= ARMV4_5_STATE_ARM
;
984 /* flash write code */
985 if (!cfi_info
->write_algorithm
)
987 u8 write_code_buf
[14 * 4];
990 if (target_alloc_working_area(target
, 4 * 14, &cfi_info
->write_algorithm
) != ERROR_OK
)
992 WARNING("no working area available, can't do block memory writes");
993 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
996 /* write algorithm code to working area */
997 if (bank
->bus_width
== 1)
999 for (i
= 0; i
< 14; i
++)
1000 target_buffer_set_u32(target
, write_code_buf
+ (i
*4), word_8_code
[i
]);
1002 else if (bank
->bus_width
== 2)
1004 for (i
= 0; i
< 14; i
++)
1005 target_buffer_set_u32(target
, write_code_buf
+ (i
*4), word_16_code
[i
]);
1007 else if (bank
->bus_width
== 4)
1009 for (i
= 0; i
< 14; i
++)
1010 target_buffer_set_u32(target
, write_code_buf
+ (i
*4), word_32_code
[i
]);
1014 return ERROR_FLASH_OPERATION_FAILED
;
1017 target_write_buffer(target
, cfi_info
->write_algorithm
->address
, 14 * 4, write_code_buf
);
1020 while (target_alloc_working_area(target
, buffer_size
, &source
) != ERROR_OK
)
1023 if (buffer_size
<= 256)
1025 /* if we already allocated the writing code, but failed to get a buffer, free the algorithm */
1026 if (cfi_info
->write_algorithm
)
1027 target_free_working_area(target
, cfi_info
->write_algorithm
);
1029 WARNING("no large enough working area available, can't do block memory writes");
1030 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
1034 init_reg_param(®_params
[0], "r0", 32, PARAM_OUT
);
1035 init_reg_param(®_params
[1], "r1", 32, PARAM_OUT
);
1036 init_reg_param(®_params
[2], "r2", 32, PARAM_OUT
);
1037 init_reg_param(®_params
[3], "r3", 32, PARAM_OUT
);
1038 init_reg_param(®_params
[4], "r4", 32, PARAM_IN
);
1039 init_reg_param(®_params
[5], "r5", 32, PARAM_OUT
);
1040 init_reg_param(®_params
[6], "r6", 32, PARAM_OUT
);
1042 /* prepare command and status register patterns */
1043 cfi_command(bank
, 0x40, write_command_buf
);
1044 cfi_command(bank
, 0x80, busy_pattern_buf
);
1045 cfi_command(bank
, 0x7e, error_pattern_buf
);
1047 if (bank
->bus_width
== 1)
1049 write_command_val
= write_command_buf
[0];
1050 busy_pattern_val
= busy_pattern_buf
[0];
1051 error_pattern_val
= error_pattern_buf
[0];
1053 else if (bank
->bus_width
== 2)
1055 write_command_val
= target_buffer_get_u16(target
, write_command_buf
);
1056 busy_pattern_val
= target_buffer_get_u16(target
, busy_pattern_buf
);
1057 error_pattern_val
= target_buffer_get_u16(target
, error_pattern_buf
);
1059 else if (bank
->bus_width
== 4)
1061 write_command_val
= target_buffer_get_u32(target
, write_command_buf
);
1062 busy_pattern_val
= target_buffer_get_u32(target
, busy_pattern_buf
);
1063 error_pattern_val
= target_buffer_get_u32(target
, error_pattern_buf
);
1068 u32 thisrun_count
= (count
> buffer_size
) ? buffer_size
: count
;
1070 target_write_buffer(target
, source
->address
, thisrun_count
, buffer
);
1072 buf_set_u32(reg_params
[0].value
, 0, 32, source
->address
);
1073 buf_set_u32(reg_params
[1].value
, 0, 32, address
);
1074 buf_set_u32(reg_params
[2].value
, 0, 32, thisrun_count
/ bank
->bus_width
);
1075 buf_set_u32(reg_params
[3].value
, 0, 32, write_command_val
);
1076 buf_set_u32(reg_params
[5].value
, 0, 32, busy_pattern_val
);
1077 buf_set_u32(reg_params
[6].value
, 0, 32, error_pattern_val
);
1079 if ((retval
= target
->type
->run_algorithm(target
, 0, NULL
, 7, reg_params
, cfi_info
->write_algorithm
->address
, cfi_info
->write_algorithm
->address
+ (13 * 4), 10000, &armv4_5_info
)) != ERROR_OK
)
1081 cfi_intel_clear_status_register(bank
);
1082 return ERROR_FLASH_OPERATION_FAILED
;
1085 if (buf_get_u32(reg_params
[4].value
, 0, 32) & error_pattern_val
)
1087 /* read status register (outputs debug inforation) */
1088 cfi_intel_wait_status_busy(bank
, 100);
1089 cfi_intel_clear_status_register(bank
);
1090 return ERROR_FLASH_OPERATION_FAILED
;
1093 buffer
+= thisrun_count
;
1094 address
+= thisrun_count
;
1095 count
-= thisrun_count
;
1098 target_free_working_area(target
, source
);
1100 destroy_reg_param(®_params
[0]);
1101 destroy_reg_param(®_params
[1]);
1102 destroy_reg_param(®_params
[2]);
1103 destroy_reg_param(®_params
[3]);
1104 destroy_reg_param(®_params
[4]);
1105 destroy_reg_param(®_params
[5]);
1106 destroy_reg_param(®_params
[6]);
1111 int cfi_spansion_write_block(struct flash_bank_s
*bank
, u8
*buffer
, u32 address
, u32 count
)
1113 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
1114 cfi_spansion_pri_ext_t
*pri_ext
= cfi_info
->pri_ext
;
1115 target_t
*target
= bank
->target
;
1116 reg_param_t reg_params
[10];
1117 armv4_5_algorithm_t armv4_5_info
;
1118 working_area_t
*source
;
1119 u32 buffer_size
= 32768;
1120 u8 write_command
[CFI_MAX_BUS_WIDTH
];
1124 int exit_code
= ERROR_OK
;
1126 /* input parameters - */
1127 /* R0 = source address */
1128 /* R1 = destination address */
1129 /* R2 = number of writes */
1130 /* R3 = flash write command */
1131 /* R4 = constant to mask DQ7 bits (also used for Dq5 with shift) */
1132 /* output parameters - */
1133 /* R5 = 0x80 ok 0x00 bad */
1134 /* temp registers - */
1135 /* R6 = value read from flash to test status */
1136 /* R7 = holding register */
1137 /* unlock registers - */
1138 /* R8 = unlock1_addr */
1139 /* R9 = unlock1_cmd */
1140 /* R10 = unlock2_addr */
1141 /* R11 = unlock2_cmd */
1143 u32 word_32_code
[] = {
1144 /* 00008100 <sp_32_code>: */
1145 0xe4905004, /* ldr r5, [r0], #4 */
1146 0xe5889000, /* str r9, [r8] */
1147 0xe58ab000, /* str r11, [r10] */
1148 0xe5883000, /* str r3, [r8] */
1149 0xe5815000, /* str r5, [r1] */
1150 0xe1a00000, /* nop */
1152 /* 00008110 <sp_32_busy>: */
1153 0xe5916000, /* ldr r6, [r1] */
1154 0xe0257006, /* eor r7, r5, r6 */
1155 0xe0147007, /* ands r7, r4, r7 */
1156 0x0a000007, /* beq 8140 <sp_32_cont> ; b if DQ7 == Data7 */
1157 0xe0166124, /* ands r6, r6, r4, lsr #2 */
1158 0x0afffff9, /* beq 8110 <sp_32_busy> ; b if DQ5 low */
1159 0xe5916000, /* ldr r6, [r1] */
1160 0xe0257006, /* eor r7, r5, r6 */
1161 0xe0147007, /* ands r7, r4, r7 */
1162 0x0a000001, /* beq 8140 <sp_32_cont> ; b if DQ7 == Data7 */
1163 0xe3a05000, /* mov r5, #0 ; 0x0 - return 0x00, error */
1164 0x1a000004, /* bne 8154 <sp_32_done> */
1166 /* 00008140 <sp_32_cont>: */
1167 0xe2522001, /* subs r2, r2, #1 ; 0x1 */
1168 0x03a05080, /* moveq r5, #128 ; 0x80 */
1169 0x0a000001, /* beq 8154 <sp_32_done> */
1170 0xe2811004, /* add r1, r1, #4 ; 0x4 */
1171 0xeaffffe8, /* b 8100 <sp_32_code> */
1173 /* 00008154 <sp_32_done>: */
1174 0xeafffffe /* b 8154 <sp_32_done> */
1177 u32 word_16_code
[] = {
1178 /* 00008158 <sp_16_code>: */
1179 0xe0d050b2, /* ldrh r5, [r0], #2 */
1180 0xe1c890b0, /* strh r9, [r8] */
1181 0xe1cab0b0, /* strh r11, [r10] */
1182 0xe1c830b0, /* strh r3, [r8] */
1183 0xe1c150b0, /* strh r5, [r1] */
1184 0xe1a00000, /* nop (mov r0,r0) */
1186 /* 00008168 <sp_16_busy>: */
1187 0xe1d160b0, /* ldrh r6, [r1] */
1188 0xe0257006, /* eor r7, r5, r6 */
1189 0xe0147007, /* ands r7, r4, r7 */
1190 0x0a000007, /* beq 8198 <sp_16_cont> */
1191 0xe0166124, /* ands r6, r6, r4, lsr #2 */
1192 0x0afffff9, /* beq 8168 <sp_16_busy> */
1193 0xe1d160b0, /* ldrh r6, [r1] */
1194 0xe0257006, /* eor r7, r5, r6 */
1195 0xe0147007, /* ands r7, r4, r7 */
1196 0x0a000001, /* beq 8198 <sp_16_cont> */
1197 0xe3a05000, /* mov r5, #0 ; 0x0 */
1198 0x1a000004, /* bne 81ac <sp_16_done> */
1200 /* 00008198 <sp_16_cont>: */
1201 0xe2522001, /* subs r2, r2, #1 ; 0x1 */
1202 0x03a05080, /* moveq r5, #128 ; 0x80 */
1203 0x0a000001, /* beq 81ac <sp_16_done> */
1204 0xe2811002, /* add r1, r1, #2 ; 0x2 */
1205 0xeaffffe8, /* b 8158 <sp_16_code> */
1207 /* 000081ac <sp_16_done>: */
1208 0xeafffffe /* b 81ac <sp_16_done> */
1211 u32 word_8_code
[] = {
1212 /* 000081b0 <sp_16_code_end>: */
1213 0xe4d05001, /* ldrb r5, [r0], #1 */
1214 0xe5c89000, /* strb r9, [r8] */
1215 0xe5cab000, /* strb r11, [r10] */
1216 0xe5c83000, /* strb r3, [r8] */
1217 0xe5c15000, /* strb r5, [r1] */
1218 0xe1a00000, /* nop (mov r0,r0) */
1220 /* 000081c0 <sp_8_busy>: */
1221 0xe5d16000, /* ldrb r6, [r1] */
1222 0xe0257006, /* eor r7, r5, r6 */
1223 0xe0147007, /* ands r7, r4, r7 */
1224 0x0a000007, /* beq 81f0 <sp_8_cont> */
1225 0xe0166124, /* ands r6, r6, r4, lsr #2 */
1226 0x0afffff9, /* beq 81c0 <sp_8_busy> */
1227 0xe5d16000, /* ldrb r6, [r1] */
1228 0xe0257006, /* eor r7, r5, r6 */
1229 0xe0147007, /* ands r7, r4, r7 */
1230 0x0a000001, /* beq 81f0 <sp_8_cont> */
1231 0xe3a05000, /* mov r5, #0 ; 0x0 */
1232 0x1a000004, /* bne 8204 <sp_8_done> */
1234 /* 000081f0 <sp_8_cont>: */
1235 0xe2522001, /* subs r2, r2, #1 ; 0x1 */
1236 0x03a05080, /* moveq r5, #128 ; 0x80 */
1237 0x0a000001, /* beq 8204 <sp_8_done> */
1238 0xe2811001, /* add r1, r1, #1 ; 0x1 */
1239 0xeaffffe8, /* b 81b0 <sp_16_code_end> */
1241 /* 00008204 <sp_8_done>: */
1242 0xeafffffe /* b 8204 <sp_8_done> */
1245 armv4_5_info
.common_magic
= ARMV4_5_COMMON_MAGIC
;
1246 armv4_5_info
.core_mode
= ARMV4_5_MODE_SVC
;
1247 armv4_5_info
.core_state
= ARMV4_5_STATE_ARM
;
1249 /* flash write code */
1250 if (!cfi_info
->write_algorithm
)
1254 /* convert bus-width dependent algorithm code to correct endiannes */
1255 if (bank
->bus_width
== 1)
1257 code_p
= malloc(24 * 4);
1259 for (i
= 0; i
< 24; i
++)
1260 target_buffer_set_u32(target
, code_p
+ (i
*4), word_8_code
[i
]);
1262 else if (bank
->bus_width
== 2)
1264 code_p
= malloc(24 * 4);
1266 for (i
= 0; i
< 24; i
++)
1267 target_buffer_set_u32(target
, code_p
+ (i
*4), word_16_code
[i
]);
1269 else if (bank
->bus_width
== 4)
1271 code_p
= malloc(24 * 4);
1273 for (i
= 0; i
< 24; i
++)
1274 target_buffer_set_u32(target
, code_p
+ (i
*4), word_32_code
[i
]);
1278 return ERROR_FLASH_OPERATION_FAILED
;
1281 /* allocate working area */
1282 if (target_alloc_working_area(target
, 24 * 4,
1283 &cfi_info
->write_algorithm
) != ERROR_OK
)
1285 WARNING("no working area available, can't do block memory writes");
1286 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
1289 /* write algorithm code to working area */
1290 target_write_buffer(target
, cfi_info
->write_algorithm
->address
, 24 * 4, code_p
);
1295 while (target_alloc_working_area(target
, buffer_size
, &source
) != ERROR_OK
)
1298 if (buffer_size
<= 256)
1300 /* if we already allocated the writing code, but failed to get a buffer, free the algorithm */
1301 if (cfi_info
->write_algorithm
)
1302 target_free_working_area(target
, cfi_info
->write_algorithm
);
1304 WARNING("not enough working area available, can't do block memory writes");
1305 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE
;
1309 init_reg_param(®_params
[0], "r0", 32, PARAM_OUT
);
1310 init_reg_param(®_params
[1], "r1", 32, PARAM_OUT
);
1311 init_reg_param(®_params
[2], "r2", 32, PARAM_OUT
);
1312 init_reg_param(®_params
[3], "r3", 32, PARAM_OUT
);
1313 init_reg_param(®_params
[4], "r4", 32, PARAM_OUT
);
1314 init_reg_param(®_params
[5], "r5", 32, PARAM_IN
);
1315 init_reg_param(®_params
[6], "r8", 32, PARAM_OUT
);
1316 init_reg_param(®_params
[7], "r9", 32, PARAM_OUT
);
1317 init_reg_param(®_params
[8], "r10", 32, PARAM_OUT
);
1318 init_reg_param(®_params
[9], "r11", 32, PARAM_OUT
);
1322 u32 thisrun_count
= (count
> buffer_size
) ? buffer_size
: count
;
1324 target_write_buffer(target
, source
->address
, thisrun_count
, buffer
);
1326 buf_set_u32(reg_params
[0].value
, 0, 32, source
->address
);
1327 buf_set_u32(reg_params
[1].value
, 0, 32, address
);
1328 buf_set_u32(reg_params
[2].value
, 0, 32, thisrun_count
/ bank
->bus_width
);
1329 cfi_command(bank
, 0xA0, write_command
);
1330 buf_set_u32(reg_params
[3].value
, 0, 32, buf_get_u32(write_command
, 0, 32));
1331 cfi_command(bank
, 0x80, write_command
);
1332 buf_set_u32(reg_params
[4].value
, 0, 32, buf_get_u32(write_command
, 0, 32));
1333 buf_set_u32(reg_params
[6].value
, 0, 32, flash_address(bank
, 0, pri_ext
->_unlock1
));
1334 buf_set_u32(reg_params
[7].value
, 0, 32, 0xaa);
1335 buf_set_u32(reg_params
[8].value
, 0, 32, flash_address(bank
, 0, pri_ext
->_unlock2
));
1336 buf_set_u32(reg_params
[9].value
, 0, 32, 0x55);
1338 retval
= target
->type
->run_algorithm(target
, 0, NULL
, 10, reg_params
,
1339 cfi_info
->write_algorithm
->address
,
1340 cfi_info
->write_algorithm
->address
+ ((24 * 4) - 4),
1341 10000, &armv4_5_info
);
1343 status
= buf_get_u32(reg_params
[5].value
, 0, 32);
1345 if ((retval
!= ERROR_OK
) || status
!= 0x80)
1347 DEBUG("status: 0x%x", status
);
1348 exit_code
= ERROR_FLASH_OPERATION_FAILED
;
1352 buffer
+= thisrun_count
;
1353 address
+= thisrun_count
;
1354 count
-= thisrun_count
;
1357 target_free_working_area(target
, source
);
1359 destroy_reg_param(®_params
[0]);
1360 destroy_reg_param(®_params
[1]);
1361 destroy_reg_param(®_params
[2]);
1362 destroy_reg_param(®_params
[3]);
1363 destroy_reg_param(®_params
[4]);
1364 destroy_reg_param(®_params
[5]);
1365 destroy_reg_param(®_params
[6]);
1366 destroy_reg_param(®_params
[7]);
1367 destroy_reg_param(®_params
[8]);
1368 destroy_reg_param(®_params
[9]);
1373 int cfi_intel_write_word(struct flash_bank_s
*bank
, u8
*word
, u32 address
)
1375 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
1376 target_t
*target
= bank
->target
;
1379 cfi_intel_clear_status_register(bank
);
1380 cfi_command(bank
, 0x40, command
);
1381 target
->type
->write_memory(target
, address
, bank
->bus_width
, 1, command
);
1383 target
->type
->write_memory(target
, address
, bank
->bus_width
, 1, word
);
1385 if (cfi_intel_wait_status_busy(bank
, 1000 * (1 << cfi_info
->word_write_timeout_max
)) != 0x80)
1387 cfi_command(bank
, 0xff, command
);
1388 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
1390 ERROR("couldn't write word at base 0x%x, address %x", bank
->base
, address
);
1391 return ERROR_FLASH_OPERATION_FAILED
;
1397 int cfi_spansion_write_word(struct flash_bank_s
*bank
, u8
*word
, u32 address
)
1399 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
1400 cfi_spansion_pri_ext_t
*pri_ext
= cfi_info
->pri_ext
;
1401 target_t
*target
= bank
->target
;
1404 cfi_command(bank
, 0xaa, command
);
1405 target
->type
->write_memory(target
, flash_address(bank
, 0, pri_ext
->_unlock1
), bank
->bus_width
, 1, command
);
1407 cfi_command(bank
, 0x55, command
);
1408 target
->type
->write_memory(target
, flash_address(bank
, 0, pri_ext
->_unlock2
), bank
->bus_width
, 1, command
);
1410 cfi_command(bank
, 0xa0, command
);
1411 target
->type
->write_memory(target
, flash_address(bank
, 0, pri_ext
->_unlock1
), bank
->bus_width
, 1, command
);
1413 target
->type
->write_memory(target
, address
, bank
->bus_width
, 1, word
);
1415 if (cfi_spansion_wait_status_busy(bank
, 1000 * (1 << cfi_info
->word_write_timeout_max
)) != ERROR_OK
)
1417 cfi_command(bank
, 0xf0, command
);
1418 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
1420 ERROR("couldn't write word at base 0x%x, address %x", bank
->base
, address
);
1421 return ERROR_FLASH_OPERATION_FAILED
;
1427 int cfi_write_word(struct flash_bank_s
*bank
, u8
*word
, u32 address
)
1429 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
1431 switch(cfi_info
->pri_id
)
1435 return cfi_intel_write_word(bank
, word
, address
);
1438 return cfi_spansion_write_word(bank
, word
, address
);
1441 ERROR("cfi primary command set %i unsupported", cfi_info
->pri_id
);
1445 return ERROR_FLASH_OPERATION_FAILED
;
1448 int cfi_write(struct flash_bank_s
*bank
, u8
*buffer
, u32 offset
, u32 count
)
1450 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
1451 target_t
*target
= bank
->target
;
1452 u32 address
= bank
->base
+ offset
; /* address of first byte to be programmed */
1453 u32 write_p
, copy_p
;
1454 int align
; /* number of unaligned bytes */
1455 u8 current_word
[CFI_MAX_BUS_WIDTH
* 4]; /* word (bus_width size) currently being programmed */
1459 if (bank
->target
->state
!= TARGET_HALTED
)
1461 return ERROR_TARGET_NOT_HALTED
;
1464 if (offset
+ count
> bank
->size
)
1465 return ERROR_FLASH_DST_OUT_OF_BANK
;
1467 if (cfi_info
->qry
[0] != 'Q')
1468 return ERROR_FLASH_BANK_NOT_PROBED
;
1470 /* start at the first byte of the first word (bus_width size) */
1471 write_p
= address
& ~(bank
->bus_width
- 1);
1472 if ((align
= address
- write_p
) != 0)
1474 for (i
= 0; i
< bank
->bus_width
; i
++)
1475 current_word
[i
] = 0;
1478 /* copy bytes before the first write address */
1479 for (i
= 0; i
< align
; ++i
, ++copy_p
)
1482 target
->type
->read_memory(target
, copy_p
, 1, 1, &byte
);
1483 cfi_add_byte(bank
, current_word
, byte
);
1486 /* add bytes from the buffer */
1487 for (; (i
< bank
->bus_width
) && (count
> 0); i
++)
1489 cfi_add_byte(bank
, current_word
, *buffer
++);
1494 /* if the buffer is already finished, copy bytes after the last write address */
1495 for (; (count
== 0) && (i
< bank
->bus_width
); ++i
, ++copy_p
)
1498 target
->type
->read_memory(target
, copy_p
, 1, 1, &byte
);
1499 cfi_add_byte(bank
, current_word
, byte
);
1502 retval
= cfi_write_word(bank
, current_word
, write_p
);
1503 if (retval
!= ERROR_OK
)
1508 /* handle blocks of bus_size aligned bytes */
1509 switch(cfi_info
->pri_id
)
1511 /* try block writes (fails without working area) */
1514 retval
= cfi_intel_write_block(bank
, buffer
, write_p
, count
);
1517 retval
= cfi_spansion_write_block(bank
, buffer
, write_p
, count
);
1520 ERROR("cfi primary command set %i unsupported", cfi_info
->pri_id
);
1521 retval
= ERROR_FLASH_OPERATION_FAILED
;
1524 if (retval
!= ERROR_OK
)
1526 if (retval
== ERROR_TARGET_RESOURCE_NOT_AVAILABLE
)
1528 /* fall back to memory writes */
1529 while (count
> bank
->bus_width
)
1531 for (i
= 0; i
< bank
->bus_width
; i
++)
1532 current_word
[i
] = 0;
1534 for (i
= 0; i
< bank
->bus_width
; i
++)
1536 cfi_add_byte(bank
, current_word
, *buffer
++);
1539 retval
= cfi_write_word(bank
, current_word
, write_p
);
1540 if (retval
!= ERROR_OK
)
1542 write_p
+= bank
->bus_width
;
1543 count
-= bank
->bus_width
;
1550 /* handle unaligned tail bytes */
1554 for (i
= 0; i
< bank
->bus_width
; i
++)
1555 current_word
[i
] = 0;
1557 for (i
= 0; (i
< bank
->bus_width
) && (count
> 0); ++i
, ++copy_p
)
1559 cfi_add_byte(bank
, current_word
, *buffer
++);
1562 for (; i
< bank
->bus_width
; ++i
, ++copy_p
)
1565 target
->type
->read_memory(target
, copy_p
, 1, 1, &byte
);
1566 cfi_add_byte(bank
, current_word
, byte
);
1568 retval
= cfi_write_word(bank
, current_word
, write_p
);
1569 if (retval
!= ERROR_OK
)
1573 /* return to read array mode */
1574 cfi_command(bank
, 0xf0, current_word
);
1575 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, current_word
);
1576 cfi_command(bank
, 0xff, current_word
);
1577 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, current_word
);
1582 void cfi_fixup_atmel_reversed_erase_regions(flash_bank_t
*bank
, void *param
)
1584 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
1585 cfi_spansion_pri_ext_t
*pri_ext
= cfi_info
->pri_ext
;
1587 pri_ext
->_reversed_geometry
= 1;
1590 void cfi_fixup_0002_erase_regions(flash_bank_t
*bank
, void *param
)
1593 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
1594 cfi_spansion_pri_ext_t
*pri_ext
= cfi_info
->pri_ext
;
1596 if ((pri_ext
->_reversed_geometry
) || (pri_ext
->TopBottom
== 3))
1598 DEBUG("swapping reversed erase region information on cmdset 0002 device");
1600 for (i
= 0; i
< cfi_info
->num_erase_regions
/ 2; i
++)
1602 int j
= (cfi_info
->num_erase_regions
- 1) - i
;
1605 swap
= cfi_info
->erase_region_info
[i
];
1606 cfi_info
->erase_region_info
[i
] = cfi_info
->erase_region_info
[j
];
1607 cfi_info
->erase_region_info
[j
] = swap
;
1612 void cfi_fixup_0002_unlock_addresses(flash_bank_t
*bank
, void *param
)
1614 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
1615 cfi_spansion_pri_ext_t
*pri_ext
= cfi_info
->pri_ext
;
1616 cfi_unlock_addresses_t
*unlock_addresses
= param
;
1618 pri_ext
->_unlock1
= unlock_addresses
->unlock1
;
1619 pri_ext
->_unlock2
= unlock_addresses
->unlock2
;
1622 int cfi_probe(struct flash_bank_s
*bank
)
1624 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
1625 target_t
*target
= bank
->target
;
1627 int num_sectors
= 0;
1631 u32 unlock1
= 0x555;
1632 u32 unlock2
= 0x2aa;
1634 /* JEDEC standard JESD21C uses 0x5555 and 0x2aaa as unlock addresses,
1635 * while CFI compatible AMD/Spansion flashes use 0x555 and 0x2aa
1637 if (cfi_info
->jedec_probe
)
1643 /* switch to read identifier codes mode ("AUTOSELECT") */
1644 cfi_command(bank
, 0xaa, command
);
1645 target
->type
->write_memory(target
, flash_address(bank
, 0, unlock1
), bank
->bus_width
, 1, command
);
1646 cfi_command(bank
, 0x55, command
);
1647 target
->type
->write_memory(target
, flash_address(bank
, 0, unlock2
), bank
->bus_width
, 1, command
);
1648 cfi_command(bank
, 0x90, command
);
1649 target
->type
->write_memory(target
, flash_address(bank
, 0, unlock1
), bank
->bus_width
, 1, command
);
1651 if (bank
->chip_width
== 1)
1653 u8 manufacturer
, device_id
;
1654 target_read_u8(target
, bank
->base
+ 0x0, &manufacturer
);
1655 target_read_u8(target
, bank
->base
+ 0x1, &device_id
);
1656 cfi_info
->manufacturer
= manufacturer
;
1657 cfi_info
->device_id
= device_id
;
1659 else if (bank
->chip_width
== 2)
1661 target_read_u16(target
, bank
->base
+ 0x0, &cfi_info
->manufacturer
);
1662 target_read_u16(target
, bank
->base
+ 0x2, &cfi_info
->device_id
);
1665 /* switch back to read array mode */
1666 cfi_command(bank
, 0xf0, command
);
1667 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x00), bank
->bus_width
, 1, command
);
1668 cfi_command(bank
, 0xff, command
);
1669 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x00), bank
->bus_width
, 1, command
);
1671 cfi_fixup(bank
, cfi_jedec_fixups
);
1673 /* query only if this is a CFI compatible flash,
1674 * otherwise the relevant info has already been filled in
1676 if (cfi_info
->not_cfi
== 0)
1678 /* enter CFI query mode
1679 * according to JEDEC Standard No. 68.01,
1680 * a single bus sequence with address = 0x55, data = 0x98 should put
1681 * the device into CFI query mode.
1683 * SST flashes clearly violate this, and we will consider them incompatbile for now
1685 cfi_command(bank
, 0x98, command
);
1686 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x55), bank
->bus_width
, 1, command
);
1688 cfi_info
->qry
[0] = cfi_query_u8(bank
, 0, 0x10);
1689 cfi_info
->qry
[1] = cfi_query_u8(bank
, 0, 0x11);
1690 cfi_info
->qry
[2] = cfi_query_u8(bank
, 0, 0x12);
1692 DEBUG("CFI qry returned: 0x%2.2x 0x%2.2x 0x%2.2x", cfi_info
->qry
[0], cfi_info
->qry
[1], cfi_info
->qry
[2]);
1694 if ((cfi_info
->qry
[0] != 'Q') || (cfi_info
->qry
[1] != 'R') || (cfi_info
->qry
[2] != 'Y'))
1696 cfi_command(bank
, 0xf0, command
);
1697 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
1698 cfi_command(bank
, 0xff, command
);
1699 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
1700 return ERROR_FLASH_BANK_INVALID
;
1703 cfi_info
->pri_id
= cfi_query_u16(bank
, 0, 0x13);
1704 cfi_info
->pri_addr
= cfi_query_u16(bank
, 0, 0x15);
1705 cfi_info
->alt_id
= cfi_query_u16(bank
, 0, 0x17);
1706 cfi_info
->alt_addr
= cfi_query_u16(bank
, 0, 0x19);
1708 DEBUG("qry: '%c%c%c', pri_id: 0x%4.4x, pri_addr: 0x%4.4x, alt_id: 0x%4.4x, alt_addr: 0x%4.4x", cfi_info
->qry
[0], cfi_info
->qry
[1], cfi_info
->qry
[2], cfi_info
->pri_id
, cfi_info
->pri_addr
, cfi_info
->alt_id
, cfi_info
->alt_addr
);
1710 cfi_info
->vcc_min
= cfi_query_u8(bank
, 0, 0x1b);
1711 cfi_info
->vcc_max
= cfi_query_u8(bank
, 0, 0x1c);
1712 cfi_info
->vpp_min
= cfi_query_u8(bank
, 0, 0x1d);
1713 cfi_info
->vpp_max
= cfi_query_u8(bank
, 0, 0x1e);
1714 cfi_info
->word_write_timeout_typ
= cfi_query_u8(bank
, 0, 0x1f);
1715 cfi_info
->buf_write_timeout_typ
= cfi_query_u8(bank
, 0, 0x20);
1716 cfi_info
->block_erase_timeout_typ
= cfi_query_u8(bank
, 0, 0x21);
1717 cfi_info
->chip_erase_timeout_typ
= cfi_query_u8(bank
, 0, 0x22);
1718 cfi_info
->word_write_timeout_max
= cfi_query_u8(bank
, 0, 0x23);
1719 cfi_info
->buf_write_timeout_max
= cfi_query_u8(bank
, 0, 0x24);
1720 cfi_info
->block_erase_timeout_max
= cfi_query_u8(bank
, 0, 0x25);
1721 cfi_info
->chip_erase_timeout_max
= cfi_query_u8(bank
, 0, 0x26);
1723 DEBUG("Vcc min: %1.1x.%1.1x, Vcc max: %1.1x.%1.1x, Vpp min: %1.1x.%1.1x, Vpp max: %1.1x.%1.1x",
1724 (cfi_info
->vcc_min
& 0xf0) >> 4, cfi_info
->vcc_min
& 0x0f,
1725 (cfi_info
->vcc_max
& 0xf0) >> 4, cfi_info
->vcc_max
& 0x0f,
1726 (cfi_info
->vpp_min
& 0xf0) >> 4, cfi_info
->vpp_min
& 0x0f,
1727 (cfi_info
->vpp_max
& 0xf0) >> 4, cfi_info
->vpp_max
& 0x0f);
1728 DEBUG("typ. word write timeout: %u, typ. buf write timeout: %u, typ. block erase timeout: %u, typ. chip erase timeout: %u", 1 << cfi_info
->word_write_timeout_typ
, 1 << cfi_info
->buf_write_timeout_typ
,
1729 1 << cfi_info
->block_erase_timeout_typ
, 1 << cfi_info
->chip_erase_timeout_typ
);
1730 DEBUG("max. word write timeout: %u, max. buf write timeout: %u, max. block erase timeout: %u, max. chip erase timeout: %u", (1 << cfi_info
->word_write_timeout_max
) * (1 << cfi_info
->word_write_timeout_typ
),
1731 (1 << cfi_info
->buf_write_timeout_max
) * (1 << cfi_info
->buf_write_timeout_typ
),
1732 (1 << cfi_info
->block_erase_timeout_max
) * (1 << cfi_info
->block_erase_timeout_typ
),
1733 (1 << cfi_info
->chip_erase_timeout_max
) * (1 << cfi_info
->chip_erase_timeout_typ
));
1735 cfi_info
->dev_size
= cfi_query_u8(bank
, 0, 0x27);
1736 cfi_info
->interface_desc
= cfi_query_u16(bank
, 0, 0x28);
1737 cfi_info
->max_buf_write_size
= cfi_query_u16(bank
, 0, 0x2a);
1738 cfi_info
->num_erase_regions
= cfi_query_u8(bank
, 0, 0x2c);
1740 DEBUG("size: 0x%x, interface desc: %i, max buffer write size: %x", 1 << cfi_info
->dev_size
, cfi_info
->interface_desc
, (1 << cfi_info
->max_buf_write_size
));
1742 if (((1 << cfi_info
->dev_size
) * bank
->bus_width
/ bank
->chip_width
) != bank
->size
)
1744 WARNING("configuration specifies 0x%x size, but a 0x%x size flash was found", bank
->size
, 1 << cfi_info
->dev_size
);
1747 if (cfi_info
->num_erase_regions
)
1749 cfi_info
->erase_region_info
= malloc(4 * cfi_info
->num_erase_regions
);
1750 for (i
= 0; i
< cfi_info
->num_erase_regions
; i
++)
1752 cfi_info
->erase_region_info
[i
] = cfi_query_u32(bank
, 0, 0x2d + (4 * i
));
1753 DEBUG("erase region[%i]: %i blocks of size 0x%x", i
, (cfi_info
->erase_region_info
[i
] & 0xffff) + 1, (cfi_info
->erase_region_info
[i
] >> 16) * 256);
1758 cfi_info
->erase_region_info
= NULL
;
1761 /* We need to read the primary algorithm extended query table before calculating
1762 * the sector layout to be able to apply fixups
1764 switch(cfi_info
->pri_id
)
1766 /* Intel command set (standard and extended) */
1769 cfi_read_intel_pri_ext(bank
);
1771 /* AMD/Spansion, Atmel, ... command set */
1773 cfi_read_0002_pri_ext(bank
);
1776 ERROR("cfi primary command set %i unsupported", cfi_info
->pri_id
);
1780 /* return to read array mode
1781 * we use both reset commands, as some Intel flashes fail to recognize the 0xF0 command
1783 cfi_command(bank
, 0xf0, command
);
1784 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
1785 cfi_command(bank
, 0xff, command
);
1786 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
1789 /* apply fixups depending on the primary command set */
1790 switch(cfi_info
->pri_id
)
1792 /* Intel command set (standard and extended) */
1795 cfi_fixup(bank
, cfi_0001_fixups
);
1797 /* AMD/Spansion, Atmel, ... command set */
1799 cfi_fixup(bank
, cfi_0002_fixups
);
1802 ERROR("cfi primary command set %i unsupported", cfi_info
->pri_id
);
1806 if (cfi_info
->num_erase_regions
== 0)
1808 /* a device might have only one erase block, spanning the whole device */
1809 bank
->num_sectors
= 1;
1810 bank
->sectors
= malloc(sizeof(flash_sector_t
));
1812 bank
->sectors
[sector
].offset
= 0x0;
1813 bank
->sectors
[sector
].size
= bank
->size
;
1814 bank
->sectors
[sector
].is_erased
= -1;
1815 bank
->sectors
[sector
].is_protected
= -1;
1819 for (i
= 0; i
< cfi_info
->num_erase_regions
; i
++)
1821 num_sectors
+= (cfi_info
->erase_region_info
[i
] & 0xffff) + 1;
1824 bank
->num_sectors
= num_sectors
;
1825 bank
->sectors
= malloc(sizeof(flash_sector_t
) * num_sectors
);
1827 for (i
= 0; i
< cfi_info
->num_erase_regions
; i
++)
1830 for (j
= 0; j
< (cfi_info
->erase_region_info
[i
] & 0xffff) + 1; j
++)
1832 bank
->sectors
[sector
].offset
= offset
;
1833 bank
->sectors
[sector
].size
= ((cfi_info
->erase_region_info
[i
] >> 16) * 256) * bank
->bus_width
/ bank
->chip_width
;
1834 offset
+= bank
->sectors
[sector
].size
;
1835 bank
->sectors
[sector
].is_erased
= -1;
1836 bank
->sectors
[sector
].is_protected
= -1;
1845 int cfi_erase_check(struct flash_bank_s
*bank
)
1847 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
1848 target_t
*target
= bank
->target
;
1852 if (!cfi_info
->erase_check_algorithm
)
1854 u32 erase_check_code
[] =
1856 0xe4d03001, /* ldrb r3, [r0], #1 */
1857 0xe0022003, /* and r2, r2, r3 */
1858 0xe2511001, /* subs r1, r1, #1 */
1859 0x1afffffb, /* b -4 */
1860 0xeafffffe /* b 0 */
1863 /* make sure we have a working area */
1864 if (target_alloc_working_area(target
, 20, &cfi_info
->erase_check_algorithm
) != ERROR_OK
)
1866 WARNING("no working area available, falling back to slow memory reads");
1870 u8 erase_check_code_buf
[5 * 4];
1872 for (i
= 0; i
< 5; i
++)
1873 target_buffer_set_u32(target
, erase_check_code_buf
+ (i
*4), erase_check_code
[i
]);
1875 /* write algorithm code to working area */
1876 target
->type
->write_memory(target
, cfi_info
->erase_check_algorithm
->address
, 4, 5, erase_check_code_buf
);
1880 if (!cfi_info
->erase_check_algorithm
)
1882 u32
*buffer
= malloc(4096);
1884 for (i
= 0; i
< bank
->num_sectors
; i
++)
1886 u32 address
= bank
->base
+ bank
->sectors
[i
].offset
;
1887 u32 size
= bank
->sectors
[i
].size
;
1888 u32 check
= 0xffffffffU
;
1893 u32 thisrun_size
= (size
> 4096) ? 4096 : size
;
1896 target
->type
->read_memory(target
, address
, 4, thisrun_size
/ 4, (u8
*)buffer
);
1898 for (j
= 0; j
< thisrun_size
/ 4; j
++)
1901 if (check
!= 0xffffffff)
1907 size
-= thisrun_size
;
1908 address
+= thisrun_size
;
1911 bank
->sectors
[i
].is_erased
= erased
;
1918 for (i
= 0; i
< bank
->num_sectors
; i
++)
1920 u32 address
= bank
->base
+ bank
->sectors
[i
].offset
;
1921 u32 size
= bank
->sectors
[i
].size
;
1923 reg_param_t reg_params
[3];
1924 armv4_5_algorithm_t armv4_5_info
;
1926 armv4_5_info
.common_magic
= ARMV4_5_COMMON_MAGIC
;
1927 armv4_5_info
.core_mode
= ARMV4_5_MODE_SVC
;
1928 armv4_5_info
.core_state
= ARMV4_5_STATE_ARM
;
1930 init_reg_param(®_params
[0], "r0", 32, PARAM_OUT
);
1931 buf_set_u32(reg_params
[0].value
, 0, 32, address
);
1933 init_reg_param(®_params
[1], "r1", 32, PARAM_OUT
);
1934 buf_set_u32(reg_params
[1].value
, 0, 32, size
);
1936 init_reg_param(®_params
[2], "r2", 32, PARAM_IN_OUT
);
1937 buf_set_u32(reg_params
[2].value
, 0, 32, 0xff);
1939 if ((retval
= target
->type
->run_algorithm(target
, 0, NULL
, 3, reg_params
, cfi_info
->erase_check_algorithm
->address
, cfi_info
->erase_check_algorithm
->address
+ 0x10, 10000, &armv4_5_info
)) != ERROR_OK
)
1940 return ERROR_FLASH_OPERATION_FAILED
;
1942 if (buf_get_u32(reg_params
[2].value
, 0, 32) == 0xff)
1943 bank
->sectors
[i
].is_erased
= 1;
1945 bank
->sectors
[i
].is_erased
= 0;
1947 destroy_reg_param(®_params
[0]);
1948 destroy_reg_param(®_params
[1]);
1949 destroy_reg_param(®_params
[2]);
1956 int cfi_intel_protect_check(struct flash_bank_s
*bank
)
1958 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
1959 cfi_intel_pri_ext_t
*pri_ext
= cfi_info
->pri_ext
;
1960 target_t
*target
= bank
->target
;
1961 u8 command
[CFI_MAX_BUS_WIDTH
];
1964 /* check if block lock bits are supported on this device */
1965 if (!(pri_ext
->blk_status_reg_mask
& 0x1))
1966 return ERROR_FLASH_OPERATION_FAILED
;
1968 cfi_command(bank
, 0x90, command
);
1969 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x55), bank
->bus_width
, 1, command
);
1971 for (i
= 0; i
< bank
->num_sectors
; i
++)
1973 u8 block_status
= cfi_get_u8(bank
, i
, 0x2);
1975 if (block_status
& 1)
1976 bank
->sectors
[i
].is_protected
= 1;
1978 bank
->sectors
[i
].is_protected
= 0;
1981 cfi_command(bank
, 0xff, command
);
1982 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
1987 int cfi_spansion_protect_check(struct flash_bank_s
*bank
)
1989 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
1990 cfi_spansion_pri_ext_t
*pri_ext
= cfi_info
->pri_ext
;
1991 target_t
*target
= bank
->target
;
1995 cfi_command(bank
, 0xaa, command
);
1996 target
->type
->write_memory(target
, flash_address(bank
, 0, pri_ext
->_unlock1
), bank
->bus_width
, 1, command
);
1998 cfi_command(bank
, 0x55, command
);
1999 target
->type
->write_memory(target
, flash_address(bank
, 0, pri_ext
->_unlock2
), bank
->bus_width
, 1, command
);
2001 cfi_command(bank
, 0x90, command
);
2002 target
->type
->write_memory(target
, flash_address(bank
, 0, pri_ext
->_unlock1
), bank
->bus_width
, 1, command
);
2004 for (i
= 0; i
< bank
->num_sectors
; i
++)
2006 u8 block_status
= cfi_get_u8(bank
, i
, 0x2);
2008 if (block_status
& 1)
2009 bank
->sectors
[i
].is_protected
= 1;
2011 bank
->sectors
[i
].is_protected
= 0;
2014 cfi_command(bank
, 0xf0, command
);
2015 target
->type
->write_memory(target
, flash_address(bank
, 0, 0x0), bank
->bus_width
, 1, command
);
2020 int cfi_protect_check(struct flash_bank_s
*bank
)
2022 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
2024 if (cfi_info
->qry
[0] != 'Q')
2025 return ERROR_FLASH_BANK_NOT_PROBED
;
2027 switch(cfi_info
->pri_id
)
2031 return cfi_intel_protect_check(bank
);
2034 return cfi_spansion_protect_check(bank
);
2037 ERROR("cfi primary command set %i unsupported", cfi_info
->pri_id
);
2044 int cfi_info(struct flash_bank_s
*bank
, char *buf
, int buf_size
)
2047 cfi_flash_bank_t
*cfi_info
= bank
->driver_priv
;
2049 if (cfi_info
->qry
[0] == -1)
2051 printed
= snprintf(buf
, buf_size
, "\ncfi flash bank not probed yet\n");
2055 printed
= snprintf(buf
, buf_size
, "\ncfi information:\n");
2057 buf_size
-= printed
;
2059 printed
= snprintf(buf
, buf_size
, "\nmfr: 0x%4.4x, id:0x%4.4x\n",
2060 cfi_info
->manufacturer
, cfi_info
->device_id
);
2062 buf_size
-= printed
;
2064 printed
= snprintf(buf
, buf_size
, "qry: '%c%c%c', pri_id: 0x%4.4x, pri_addr: 0x%4.4x, alt_id: 0x%4.4x, alt_addr: 0x%4.4x\n", cfi_info
->qry
[0], cfi_info
->qry
[1], cfi_info
->qry
[2], cfi_info
->pri_id
, cfi_info
->pri_addr
, cfi_info
->alt_id
, cfi_info
->alt_addr
);
2066 buf_size
-= printed
;
2068 printed
= snprintf(buf
, buf_size
, "Vcc min: %1.1x.%1.1x, Vcc max: %1.1x.%1.1x, Vpp min: %1.1x.%1.1x, Vpp max: %1.1x.%1.1x\n", (cfi_info
->vcc_min
& 0xf0) >> 4, cfi_info
->vcc_min
& 0x0f,
2069 (cfi_info
->vcc_max
& 0xf0) >> 4, cfi_info
->vcc_max
& 0x0f,
2070 (cfi_info
->vpp_min
& 0xf0) >> 4, cfi_info
->vpp_min
& 0x0f,
2071 (cfi_info
->vpp_max
& 0xf0) >> 4, cfi_info
->vpp_max
& 0x0f);
2073 buf_size
-= printed
;
2075 printed
= snprintf(buf
, buf_size
, "typ. word write timeout: %u, typ. buf write timeout: %u, typ. block erase timeout: %u, typ. chip erase timeout: %u\n", 1 << cfi_info
->word_write_timeout_typ
, 1 << cfi_info
->buf_write_timeout_typ
,
2076 1 << cfi_info
->block_erase_timeout_typ
, 1 << cfi_info
->chip_erase_timeout_typ
);
2078 buf_size
-= printed
;
2080 printed
= snprintf(buf
, buf_size
, "max. word write timeout: %u, max. buf write timeout: %u, max. block erase timeout: %u, max. chip erase timeout: %u\n", (1 << cfi_info
->word_write_timeout_max
) * (1 << cfi_info
->word_write_timeout_typ
),
2081 (1 << cfi_info
->buf_write_timeout_max
) * (1 << cfi_info
->buf_write_timeout_typ
),
2082 (1 << cfi_info
->block_erase_timeout_max
) * (1 << cfi_info
->block_erase_timeout_typ
),
2083 (1 << cfi_info
->chip_erase_timeout_max
) * (1 << cfi_info
->chip_erase_timeout_typ
));
2085 buf_size
-= printed
;
2087 printed
= snprintf(buf
, buf_size
, "size: 0x%x, interface desc: %i, max buffer write size: %x\n", 1 << cfi_info
->dev_size
, cfi_info
->interface_desc
, cfi_info
->max_buf_write_size
);
2089 buf_size
-= printed
;
2091 switch(cfi_info
->pri_id
)
2095 cfi_intel_info(bank
, buf
, buf_size
);
2098 cfi_spansion_info(bank
, buf
, buf_size
);
2101 ERROR("cfi primary command set %i unsupported", cfi_info
->pri_id
);
Linking to existing account procedure
If you already have an account and want to add another login method
you
MUST first sign in with your existing account and
then change URL to read
https://review.openocd.org/login/?link
to get to this page again but this time it'll work for linking. Thank you.
SSH host keys fingerprints
1024 SHA256:YKx8b7u5ZWdcbp7/4AeXNaqElP49m6QrwfXaqQGJAOk gerrit-code-review@openocd.zylin.com (DSA)
384 SHA256:jHIbSQa4REvwCFG4cq5LBlBLxmxSqelQPem/EXIrxjk gerrit-code-review@openocd.org (ECDSA)
521 SHA256:UAOPYkU9Fjtcao0Ul/Rrlnj/OsQvt+pgdYSZ4jOYdgs gerrit-code-review@openocd.org (ECDSA)
256 SHA256:A13M5QlnozFOvTllybRZH6vm7iSt0XLxbA48yfc2yfY gerrit-code-review@openocd.org (ECDSA)
256 SHA256:spYMBqEYoAOtK7yZBrcwE8ZpYt6b68Cfh9yEVetvbXg gerrit-code-review@openocd.org (ED25519)
+--[ED25519 256]--+
|=.. |
|+o.. . |
|*.o . . |
|+B . . . |
|Bo. = o S |
|Oo.+ + = |
|oB=.* = . o |
| =+=.+ + E |
|. .=o . o |
+----[SHA256]-----+
2048 SHA256:0Onrb7/PHjpo6iVZ7xQX2riKN83FJ3KGU0TvI0TaFG4 gerrit-code-review@openocd.zylin.com (RSA)