summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorStefan Tauner <stefan.tauner@alumni.tuwien.ac.at>2014-08-05 23:28:47 +0000
committerStefan Tauner <stefan.tauner@alumni.tuwien.ac.at>2014-08-05 23:28:47 +0000
commit405c39bc9be8002524d4911564515876a5f4f7ba (patch)
tree89281c1e08bcc265ac38ba1f1497462f97627fbc
parent193671c90be7268b178a9a369bad490dacacc83a (diff)
downloadflashrom-405c39bc9be8002524d4911564515876a5f4f7ba.zip
flashrom-405c39bc9be8002524d4911564515876a5f4f7ba.tar.gz
ichspi: fix missing set_addr on erases and possible crossings of 256 B boundaries
Apparently the erase function did never set any address before issuing the erase commands. How could this ever work? Also, according to PCH documentation crossing 256 byte boundaries is invalid and may cause wraparound due to the flash chip's pages. Check for this on reads as well as writes. Binary file (standard input) matches Corresponding to flashrom svn r1837.
-rw-r--r--ichspi.c8
1 files changed, 8 insertions, 0 deletions
diff --git a/ichspi.c b/ichspi.c
index 90bb0de..5d37d06 100644
--- a/ichspi.c
+++ b/ichspi.c
@@ -1272,6 +1272,7 @@ static int ich_hwseq_block_erase(struct flashctx *flash, unsigned int addr,
}
msg_pdbg("Erasing %d bytes starting at 0x%06x.\n", len, addr);
+ ich_hwseq_set_addr(addr);
/* make sure FDONE, FCERR, AEL are cleared by writing 1 to them */
REGWRITE16(ICH9_REG_HSFS, REGREAD16(ICH9_REG_HSFS));
@@ -1307,7 +1308,11 @@ static int ich_hwseq_read(struct flashctx *flash, uint8_t *buf,
REGWRITE16(ICH9_REG_HSFS, REGREAD16(ICH9_REG_HSFS));
while (len > 0) {
+ /* Obey programmer limit... */
block_len = min(len, flash->mst->opaque.max_data_read);
+ /* as well as flash chip page borders as demanded in the Intel datasheets. */
+ block_len = min(block_len, 256 - (addr & 0xFF));
+
ich_hwseq_set_addr(addr);
hsfc = REGREAD16(ICH9_REG_HSFC);
hsfc &= ~HSFC_FCYCLE; /* set read operation */
@@ -1345,7 +1350,10 @@ static int ich_hwseq_write(struct flashctx *flash, const uint8_t *buf, unsigned
while (len > 0) {
ich_hwseq_set_addr(addr);
+ /* Obey programmer limit... */
block_len = min(len, flash->mst->opaque.max_data_write);
+ /* as well as flash chip page borders as demanded in the Intel datasheets. */
+ block_len = min(block_len, 256 - (addr & 0xFF));
ich_fill_data(buf, block_len, ICH9_REG_FDATA0);
hsfc = REGREAD16(ICH9_REG_HSFC);
hsfc &= ~HSFC_FCYCLE; /* clear operation */
OpenPOWER on IntegriCloud