Message ID | BD79186B4FD85F4B8E60E381CAEE1909AEEF6B@mi8nycmail19.Mi8.com |
---|---|
State | Not Applicable |
Headers | show |
diff --git a/drivers/mtd/devices/m25p80.c b/drivers/mtd/devices/m25p80.c index b35c333..ee6dd52 100644 --- a/drivers/mtd/devices/m25p80.c +++ b/drivers/mtd/devices/m25p80.c @@ -41,6 +41,7 @@ #define OPCODE_BE_32K 0x52 /* Erase 32KiB block */ #define OPCODE_SE 0xd8 /* Sector erase (usually 64KiB) */ #define OPCODE_RDID 0x9f /* Read JEDEC ID */ +#define OPCODE_RDID_NON_JEDEC 0x90 /* Read non-JEDEC ID */ /* Status Register bits. */
Hello all, This patch allows the m25p80 driver to support non-JEDEC ID devices. It has been tested on an EP93xx based ARM platform with a SST25LF020A 2Mbit SPI Serial Flash device. Any comments would be appreciated. Thanks, Signed-off-by: H Hartley Sweeten <hsweeten@visionengravers.com> --- #define SR_WIP 1 /* Write in progress */ @@ -507,13 +508,17 @@ static struct flash_info __devinitdata m25p_data [] = { { "w25x16", 0xef3015, 64 * 1024, 32, SECT_4K, }, { "w25x32", 0xef3016, 64 * 1024, 64, SECT_4K, }, { "w25x64", 0xef3017, 64 * 1024, 128, SECT_4K, }, + + /* Non JEDEC ID SST -- large erase sizes are "overlays", "sectors" are 4K */ + { "sst25lf020a", 0xbf43, 32 * 1024, 8, SECT_4K, }, + { "sst25lf040a", 0xbf44, 32 * 1024, 16, SECT_4K, }, }; static struct flash_info *__devinit jedec_probe(struct spi_device *spi) { int tmp; - u8 code = OPCODE_RDID; - u8 id[3]; + u8 code[4]; + u8 id[4]; u32 jedec; struct flash_info *info; @@ -521,7 +526,8 @@ static struct flash_info *__devinit jedec_probe(struct spi_device *spi) * string for after vendor-specific data, after the three bytes * we use here. Supporting some chips might require using it. */ - tmp = spi_write_then_read(spi, &code, 1, id, 3); + code[0] = OPCODE_RDID; + tmp = spi_write_then_read(spi, code, 1, id, 3); if (tmp < 0) { DEBUG(MTD_DEBUG_LEVEL0, "%s: error %d reading JEDEC ID\n", spi->dev.bus_id, tmp); @@ -540,6 +546,31 @@ static struct flash_info *__devinit jedec_probe(struct spi_device *spi) return info; } dev_err(&spi->dev, "unrecognized JEDEC id %06x\n", jedec); + + /* Try reading the non-JEDEC Manufacture/Device ID */ + code[0] = OPCODE_RDID_NON_JEDEC; + code[1] = 0x00; + code[2] = 0x00; + code[3] = 0x00; + tmp = spi_write_then_read(spi, code, 4, id, 2); + if (tmp < 0) { + DEBUG(MTD_DEBUG_LEVEL0, "%s: error %d reading ID\n", + spi->dev.bus_id, tmp); + return NULL; + } + + jedec = id[0]; + jedec = jedec << 8; + jedec |= id[1]; + + for (tmp = 0, info = m25p_data; + tmp < ARRAY_SIZE(m25p_data); + tmp++, info++) { + if (info->jedec_id == jedec) + return info; + } + dev_err(&spi->dev, "unrecognized id %04x\n", jedec); + return NULL; }