[U-Boot] [PATCHv3 CFI flash] Work around bug in Numonyx P33/P30 256-Mbit 65nm flash chips.

Philippe De Muyter phdm at macqel.be
Mon Aug 16 15:59:05 CEST 2010


I have "ported" U-boot to a in house made board with Numonyx Axcell P33/P30
256-Mbit 65nm flash chips.

After some time :( searching for bugs in our board or soft, we have
discovered that those chips have a small but annoying bug, documented in
"Numonyx Axcell P33/P30 256-Mbit Specification Update"

It states :
When customer uses [...] block unlock, the block lock status might be
altered inadvertently. Lock status might be set to either 01h or 03h
unexpectedly (00h as expected data), which leads to program/erase failure
on certain blocks.

A working workaround is given, which I have applied and tested with success :

Workaround:  If the interval between 60h and its subsequent command
	     can be guaranteed within 20μs, Option I is recommended,
	     otherwise Option II (involves hardware) should be selected.
Option I: The table below lists the detail command sequences:
Command
	      Data bus           Address bus       Remarks
Sequence
  1              90h            Block Address
						   Read Lock Status
  2             Read         Block Address + 02h
 (2)(3)                                      (1)
3                60h           Block Address
 (2)(3)                                      (1)   Lock/Unlock/RCR Configuration
4           D0h/01h/03h        Block Address
Notes:
(1) Block Address refers to RCR configuration data only when the 60h
    command sequence is used to set RCR register combined with 03h
    subsequent command.
(2) For the third and fourth command sequences, the Block Address must
    be the same.
(3) The interval between 60h command and its subsequent D0h/01h/2Fh/03h
    commands should be less than 20μs.

And here is a log comparison of a simple (destructive) flash test without
and with the workaround.

diff -U 50 without-numonyx-workaround.log with-numonyx-workaround.log
--- without-numonyx-workaround.log	2010-08-16 15:32:34.000000000 +0200
+++ with-numonyx-workaround.log	2010-08-16 15:32:55.000000000 +0200
@@ -1,33 +1,33 @@
-U-Boot 2010.06-00696-g22b002c-dirty (Aug 16 2010 - 15:07:47)
+U-Boot 2010.06-00696-g22b002c-dirty (Aug 16 2010 - 15:25:19)
 
 CPU:   Freescale MCF5484
        CPU CLK 200 MHz BUS CLK 100 MHz
 Board: Macq Electronique ME2060
 I2C:   ready
 DRAM:  64 MiB
 FLASH: 32 MiB
 In:    serial
 Out:   serial
 Err:   serial
 Net:   FEC0, FEC1
 -> flinfo
 
 Bank # 1: CFI conformant FLASH (16 x 16)  Size: 32 MB in 259 Sectors
   Intel Extended command set, Manufacturer ID: 0x89, Device ID: 0x8922
   Erase timeout: 4096 ms, write timeout: 1 ms
   Buffer write timeout: 5 ms, buffer size: 1024 bytes
 
   Sector Start Addresses:
   FE000000   RO   FE008000   RO   FE010000   RO   FE018000   RO   FE020000   RO
   FE040000   RO   FE060000   RO   FE080000   RO   FE0A0000   RO   FE0C0000   RO
   ...
   FFF80000   RO   FFFA0000   RO   FFFC0000   RO   FFFE0000   RO
 -> protect off all
 Un-Protect Flash Bank # 1
 ................................................................................................................................................................................................................................................................... done
 -> erase all
 Erase Flash Bank # 1
 ................................................................................................................................................................................................................................................................... done
 -> cp.b 1000000 fe000000 2000000
-Copy to Flash... Flash not Erased
+Copy to Flash... done
 ->

Signed-off-by: Philippe De Muyter <phdm at macqel.be>

---
diff --git a/drivers/mtd/cfi_flash.c b/drivers/mtd/cfi_flash.c
index 2d09caf..809ff0e 100644
--- a/drivers/mtd/cfi_flash.c
+++ b/drivers/mtd/cfi_flash.c
@@ -1348,15 +1350,32 @@ int flash_real_protect (flash_info_t * info, long sector, int prot)
 		case CFI_CMDSET_INTEL_PROG_REGIONS:
 		case CFI_CMDSET_INTEL_STANDARD:
 		case CFI_CMDSET_INTEL_EXTENDED:
-			flash_write_cmd (info, sector, 0,
-					 FLASH_CMD_CLEAR_STATUS);
-			flash_write_cmd (info, sector, 0, FLASH_CMD_PROTECT);
-			if (prot)
-				flash_write_cmd (info, sector, 0,
-					FLASH_CMD_PROTECT_SET);
-			else
+			/*
+			 * see errata called
+			 * "Numonyx Axcell P33/P30 Specification Update" :)
+			 */
+			flash_write_cmd (info, sector, 0, FLASH_CMD_READ_ID);
+			if (!flash_isequal (info, sector, FLASH_OFFSET_PROTECT,
+					    prot)) {
+				/*
+				 * cmd must come before FLASH_CMD_PROTECT + 20us
+				 * Disable interrupts which might cause a timeout here.
+				 */
+				int flag = disable_interrupts ();
+				unsigned short cmd;
+
+				if (prot)
+					cmd = FLASH_CMD_PROTECT_SET;
+				else
+					cmd = FLASH_CMD_PROTECT_CLEAR;
+
 				flash_write_cmd (info, sector, 0,
-					FLASH_CMD_PROTECT_CLEAR);
+						  FLASH_CMD_PROTECT);
+				flash_write_cmd (info, sector, 0, cmd);
+				/* re-enable interrupts if necessary */
+				if (flag)
+					enable_interrupts ();
+			}
 			break;
 		case CFI_CMDSET_AMD_EXTENDED:
 		case CFI_CMDSET_AMD_STANDARD:
-- 
Philippe De Muyter  phdm at macqel dot be  Tel +32 27029044
Macq Electronique SA  rue de l'Aeronef 2  B-1140 Bruxelles  Fax +32 27029077


More information about the U-Boot mailing list