Kill a few unused functions in 82802ab.c and stm50flw0x0x.c. Replace wait_stm50flw0x0x() with wait_82802ab() as the the read id mode stuff is historic cruft that was never needed. Replace erase_82802ab_block() with erase_82802ab_block_withunlock(). Factor out unlocking from erase_82802ab_block().
Signed-off-by: Carl-Daniel Hailfinger c-d.hailfinger.devel.2006@gmx.net
Index: flashrom-82802ab_stm50flw0x0x_cleanup/flashchips.c =================================================================== --- flashrom-82802ab_stm50flw0x0x_cleanup/flashchips.c (Revision 947) +++ flashrom-82802ab_stm50flw0x0x_cleanup/flashchips.c (Arbeitskopie) @@ -2315,128 +2315,128 @@ .manufacture_id = INTEL_ID, .model_id = P28F001BXB, .total_size = 128, .page_size = 128 * 1024, /* 8k + 2x4k + 112k */ .feature_bits = 0, .tested = TEST_BAD_WRITE, .probe = probe_jedec, .probe_timing = TIMING_ZERO, /* Datasheet has no timing info specified */ .block_erasers = { { .eraseblocks = { {8 * 1024, 1}, {4 * 1024, 2}, {112 * 1024, 1}, }, - .block_erase = erase_82802ab_block, + .block_erase = erase_82802ab_block_withunlock, }, }, .write = NULL, .read = read_memmapped, },
{ .vendor = "Intel", .name = "28F001BX-T", .bustype = CHIP_BUSTYPE_PARALLEL, .manufacture_id = INTEL_ID, .model_id = P28F001BXT, .total_size = 128, .page_size = 128 * 1024, /* 112k + 2x4k + 8k */ .feature_bits = 0, .tested = TEST_BAD_WRITE, .probe = probe_jedec, .probe_timing = TIMING_ZERO, /* Datasheet has no timing info specified */ .block_erasers = { { .eraseblocks = { {112 * 1024, 1}, {4 * 1024, 2}, {8 * 1024, 1}, }, - .block_erase = erase_82802ab_block, + .block_erase = erase_82802ab_block_withunlock, }, }, .write = NULL, .read = read_memmapped, },
{ .vendor = "Intel", .name = "28F004S5", .bustype = CHIP_BUSTYPE_PARALLEL, .manufacture_id = INTEL_ID, .model_id = E_28F004S5, .total_size = 512, .page_size = 256, .tested = TEST_UNTESTED, .probe = probe_82802ab, .probe_timing = TIMING_ZERO, /* Datasheet has no timing info specified */ .block_erasers = { { .eraseblocks = { {64 * 1024, 8} }, - .block_erase = erase_82802ab_block, + .block_erase = erase_82802ab_block_withunlock, }, }, .write = write_82802ab, .read = read_memmapped, },
{ .vendor = "Intel", .name = "82802AB", .bustype = CHIP_BUSTYPE_FWH, .manufacture_id = INTEL_ID, .model_id = I_82802AB, .total_size = 512, .page_size = 64 * 1024, .feature_bits = FEATURE_REGISTERMAP, - .tested = TEST_OK_PRW, + .tested = TEST_OK_PR, .probe = probe_82802ab, .probe_timing = TIMING_IGNORED, /* routine does not use probe_timing (82802ab.c) */ .block_erasers = { { .eraseblocks = { {64 * 1024, 8} }, - .block_erase = erase_82802ab_block, + .block_erase = erase_82802ab_block_withunlock, }, }, .write = write_82802ab, .read = read_memmapped, },
{ .vendor = "Intel", .name = "82802AC", .bustype = CHIP_BUSTYPE_FWH, .manufacture_id = INTEL_ID, .model_id = I_82802AC, .total_size = 1024, .page_size = 64 * 1024, .feature_bits = FEATURE_REGISTERMAP, - .tested = TEST_OK_PRW, + .tested = TEST_OK_PR, .probe = probe_82802ab, .probe_timing = TIMING_IGNORED, /* routine does not use probe_timing (82802ab.c) */ .block_erasers = { { .eraseblocks = { {64 * 1024, 16} }, - .block_erase = erase_82802ab_block, + .block_erase = erase_82802ab_block_withunlock, }, }, .write = write_82802ab, .read = read_memmapped, },
{ .vendor = "Macronix", .name = "MX25L512", .bustype = CHIP_BUSTYPE_SPI, .manufacture_id = MX_ID, .model_id = MX_25L512, .total_size = 64, .page_size = 256, .tested = TEST_UNTESTED, .probe = probe_spi_rdid, Index: flashrom-82802ab_stm50flw0x0x_cleanup/stm50flw0x0x.c =================================================================== --- flashrom-82802ab_stm50flw0x0x_cleanup/stm50flw0x0x.c (Revision 947) +++ flashrom-82802ab_stm50flw0x0x_cleanup/stm50flw0x0x.c (Arbeitskopie) @@ -20,52 +20,32 @@ */
/* * This module is designed for supporting the devices * ST M50FLW040A (not yet tested) * ST M50FLW040B (not yet tested) * ST M50FLW080A * ST M50FLW080B (not yet tested) */
#include <string.h> #include <stdlib.h> #include "flash.h" #include "flashchips.h" #include "chipdrivers.h"
-static void wait_stm50flw0x0x(chipaddr bios) -{ - chip_writeb(0x70, bios); - if ((chip_readb(bios) & 0x80) == 0) { // it's busy - while ((chip_readb(bios) & 0x80) == 0) ; - } - - // put another command to get out of status register mode - - chip_writeb(0x90, bios); - programmer_delay(10); - - chip_readb(bios); // Read device ID (to make sure?) - - // this is needed to jam it out of "read id" mode - chip_writeb(0xAA, bios + 0x5555); - chip_writeb(0x55, bios + 0x2AAA); - chip_writeb(0xF0, bios + 0x5555); -} - /* * claus.gindhart@kontron.com * The ST M50FLW080B and STM50FLW080B chips have to be unlocked, * before you can erase them or write to them. */ int unlock_block_stm50flw0x0x(struct flashchip *flash, int offset) { chipaddr wrprotect = flash->virtual_registers + 2; const uint8_t unlock_sector = 0x00; int j;
/* * These chips have to be unlocked before you can erase them or write * to them. The size of the locking sectors depends on the type * of chip. * @@ -100,104 +80,66 @@
return 0; }
int erase_block_stm50flw0x0x(struct flashchip *flash, unsigned int block, unsigned int blocksize) { chipaddr bios = flash->virtual_memory + block;
// clear status register chip_writeb(0x50, bios); printf_debug("Erase at 0x%lx\n", bios); // now start it chip_writeb(0x20, bios); chip_writeb(0xd0, bios); programmer_delay(10);
- wait_stm50flw0x0x(flash->virtual_memory); + wait_82802ab(flash->virtual_memory);
if (check_erased_range(flash, block, blocksize)) { fprintf(stderr, "ERASE FAILED!\n"); return -1; } printf("DONE BLOCK 0x%x\n", block);
return 0; }
int erase_sector_stm50flw0x0x(struct flashchip *flash, unsigned int sector, unsigned int sectorsize) { chipaddr bios = flash->virtual_memory + sector;
// clear status register chip_writeb(0x50, bios); printf_debug("Erase at 0x%lx\n", bios); // now start it chip_writeb(0x32, bios); chip_writeb(0xd0, bios); programmer_delay(10);
- wait_stm50flw0x0x(flash->virtual_memory); + wait_82802ab(flash->virtual_memory);
if (check_erased_range(flash, sector, sectorsize)) { fprintf(stderr, "ERASE FAILED!\n"); return -1; } printf("DONE BLOCK 0x%x\n", sector);
return 0; }
-int write_page_stm50flw0x0x(chipaddr bios, uint8_t *src, - chipaddr dst, int page_size) -{ - int i, rc = 0; - chipaddr d = dst; - uint8_t *s = src; - - /* transfer data from source to destination */ - for (i = 0; i < page_size; i++) { - chip_writeb(0x40, dst); - chip_writeb(*src++, dst++); - wait_stm50flw0x0x(bios); - } - -/* claus.gindhart@kontron.com - * TODO - * I think, that verification is not required, but - * i leave it in anyway - */ - dst = d; - src = s; - for (i = 0; i < page_size; i++) { - if (chip_readb(dst) != *src) { - rc = -1; - break; - } - dst++; - src++; - } - - if (rc) { - fprintf(stderr, " page 0x%lx failed!\n", - (d - bios) / page_size); - } - - return rc; -} - /* I simply erase block by block * I Chip This is not the fastest way, but it works */ int erase_stm50flw0x0x(struct flashchip *flash) { int i; int total_size = flash->total_size * 1024; int page_size = flash->page_size;
printf("Erasing page:\n"); for (i = 0; i < total_size / page_size; i++) { printf ("\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b"); printf("%04d at address: 0x%08x ", i, i * page_size); if (unlock_block_stm50flw0x0x(flash, i * page_size)) { fprintf(stderr, "UNLOCK FAILED!\n"); @@ -245,24 +187,24 @@ * Faster, because we only write, what has changed * More secure, because blocks, which are excluded * (with the exclude or layout feature) * are not erased and rewritten; data is retained also * in sudden power off situations */ chip_readn(tmpbuf, bios + i * page_size, page_size); if (!memcmp((void *)(buf + i * page_size), tmpbuf, page_size)) { printf("SKIPPED\n"); continue; }
rc = unlock_block_stm50flw0x0x(flash, i * page_size); if (!rc) rc = erase_block_stm50flw0x0x(flash, i * page_size, page_size); if (!rc) - write_page_stm50flw0x0x(bios, buf + i * page_size, + write_page_82802ab(bios, buf + i * page_size, bios + i * page_size, page_size); } printf("\n"); free(tmpbuf);
return rc; } Index: flashrom-82802ab_stm50flw0x0x_cleanup/82802ab.c =================================================================== --- flashrom-82802ab_stm50flw0x0x_cleanup/82802ab.c (Revision 947) +++ flashrom-82802ab_stm50flw0x0x_cleanup/82802ab.c (Arbeitskopie) @@ -1,20 +1,21 @@ /* * This file is part of the flashrom project. * * Copyright (C) 2000 Silicon Integrated System Corporation + * Copyright (C) 2010 Carl-Daniel Hailfinger * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */
@@ -79,79 +80,75 @@ { uint8_t status;
chip_writeb(0x70, bios); if ((chip_readb(bios) & 0x80) == 0) { // it's busy while ((chip_readb(bios) & 0x80) == 0) ; }
status = chip_readb(bios);
/* Reset to get a clean state */ chip_writeb(0xFF, bios);
return status; }
+int unlock_82802ab_block(struct flashchip *flash, unsigned int page) +{ + chipaddr wrprotect = flash->virtual_registers + page + 2; + + /* Clear write protect */ + chip_writeb(0, wrprotect); + + return 0; +} + +/* FIXME: Ugly hack. Shoud do unlock separately. */ +int erase_82802ab_block_withunlock(struct flashchip *flash, unsigned int page, unsigned int pagesize) +{ + unlock_82802ab_block(flash, page); + return erase_82802ab_block(flash, page, pagesize); +} + int erase_82802ab_block(struct flashchip *flash, unsigned int page, unsigned int pagesize) { chipaddr bios = flash->virtual_memory; - chipaddr wrprotect = flash->virtual_registers + page + 2; uint8_t status;
// clear status register chip_writeb(0x50, bios + page);
- // clear write protect - chip_writeb(0, wrprotect); - // now start it chip_writeb(0x20, bios + page); chip_writeb(0xd0, bios + page); programmer_delay(10);
// now let's see what the register is status = wait_82802ab(bios); print_82802ab_status(status);
if (check_erased_range(flash, page, pagesize)) { fprintf(stderr, "ERASE FAILED!\n"); return -1; } printf("DONE BLOCK 0x%x\n", page);
return 0; }
-int erase_82802ab(struct flashchip *flash) -{ - int i; - unsigned int total_size = flash->total_size * 1024; - - printf("total_size is %d; flash->page_size is %d\n", - total_size, flash->page_size); - for (i = 0; i < total_size; i += flash->page_size) - if (erase_82802ab_block(flash, i, flash->page_size)) { - fprintf(stderr, "ERASE FAILED!\n"); - return -1; - } - printf("DONE ERASE\n"); - - return 0; -} - void write_page_82802ab(chipaddr bios, uint8_t *src, chipaddr dst, int page_size) { int i;
for (i = 0; i < page_size; i++) { /* transfer data from source to destination */ chip_writeb(0x40, dst); chip_writeb(*src++, dst++); wait_82802ab(bios); } }
int write_82802ab(struct flashchip *flash, uint8_t *buf) { int i; @@ -171,28 +168,28 @@ printf("%04d at address: 0x%08x", i, i * page_size);
/* Auto Skip Blocks, which already contain the desired data * Faster, because we only write, what has changed * More secure, because blocks, which are excluded * (with the exclude or layout feature) * or not erased and rewritten; their data is retained also in * sudden power off situations */ chip_readn(tmpbuf, bios + i * page_size, page_size); if (!memcmp((void *)(buf + i * page_size), tmpbuf, page_size)) { printf("SKIPPED\n"); continue; }
/* erase block by block and write block by block; this is the most secure way */ - if (erase_82802ab_block(flash, i * page_size, page_size)) { + if (erase_82802ab_block_withunlock(flash, i * page_size, page_size)) { fprintf(stderr, "ERASE FAILED!\n"); return -1; } write_page_82802ab(bios, buf + i * page_size, bios + i * page_size, page_size); } printf("\n"); free(tmpbuf);
return 0; } Index: flashrom-82802ab_stm50flw0x0x_cleanup/chipdrivers.h =================================================================== --- flashrom-82802ab_stm50flw0x0x_cleanup/chipdrivers.h (Revision 947) +++ flashrom-82802ab_stm50flw0x0x_cleanup/chipdrivers.h (Arbeitskopie) @@ -43,34 +43,34 @@ int spi_block_erase_60(struct flashchip *flash, unsigned int addr, unsigned int blocklen); int spi_block_erase_c7(struct flashchip *flash, unsigned int addr, unsigned int blocklen); int spi_chip_write_1(struct flashchip *flash, uint8_t *buf); int spi_chip_write_256(struct flashchip *flash, uint8_t *buf); int spi_chip_read(struct flashchip *flash, uint8_t *buf, int start, int len); uint8_t spi_read_status_register(void); int spi_disable_blockprotect(void); int spi_byte_program(int addr, uint8_t databyte); int spi_nbyte_program(int addr, uint8_t *bytes, int len); int spi_nbyte_read(int addr, uint8_t *bytes, int len); int spi_read_chunked(struct flashchip *flash, uint8_t *buf, int start, int len, int chunksize); int spi_aai_write(struct flashchip *flash, uint8_t *buf);
/* 82802ab.c */ uint8_t wait_82802ab(chipaddr bios); int probe_82802ab(struct flashchip *flash); -int erase_82802ab(struct flashchip *flash); int erase_82802ab_block(struct flashchip *flash, unsigned int page, unsigned int pagesize); +int erase_82802ab_block_withunlock(struct flashchip *flash, unsigned int page, unsigned int pagesize); int write_82802ab(struct flashchip *flash, uint8_t *buf); void print_82802ab_status(uint8_t status); void write_page_82802ab(chipaddr bios, uint8_t *src, chipaddr dst, int page_size);
/* jedec.c */ uint8_t oddparity(uint8_t val); void toggle_ready_jedec(chipaddr dst); void data_polling_jedec(chipaddr dst, uint8_t data); int write_byte_program_jedec(chipaddr bios, uint8_t *src, chipaddr dst); int probe_jedec(struct flashchip *flash); int erase_chip_jedec(struct flashchip *flash); int write_jedec(struct flashchip *flash, uint8_t *buf); int write_jedec_1(struct flashchip *flash, uint8_t *buf); int erase_sector_jedec(struct flashchip *flash, unsigned int page, unsigned int pagesize); int erase_block_jedec(struct flashchip *flash, unsigned int page, unsigned int blocksize); @@ -112,23 +112,22 @@
/* sst_fwhub.c */ int printlock_sst_fwhub(struct flashchip *flash); int unlock_sst_fwhub(struct flashchip *flash);
/* w39v040c.c */ int printlock_w39v040c(struct flashchip *flash);
/* w39V080fa.c */ int unlock_winbond_fwhub(struct flashchip *flash);
/* w29ee011.c */ int probe_w29ee011(struct flashchip *flash);
/* stm50flw0x0x.c */ int probe_stm50flw0x0x(struct flashchip *flash); -int erase_stm50flw0x0x(struct flashchip *flash); int erase_block_stm50flw0x0x(struct flashchip *flash, unsigned int block, unsigned int blocksize); int erase_sector_stm50flw0x0x(struct flashchip *flash, unsigned int block, unsigned int blocksize); int erase_chip_stm50flw0x0x(struct flashchip *flash, unsigned int addr, unsigned int blocklen); int write_stm50flw0x0x(struct flashchip *flash, uint8_t *buf);
#endif /* !__CHIPDRIVERS_H__ */