diff options
author | Kyungmin Park <kyungmin.park@samsung.com> | 2007-02-11 20:34:39 -0500 |
---|---|---|
committer | David Woodhouse <dwmw2@infradead.org> | 2007-03-09 03:04:25 -0500 |
commit | 91014e9bfaaac32ab46ab46251d774468891bafe (patch) | |
tree | 66b468133af721a45fae9468a3b7390ea7ab1967 /drivers/mtd | |
parent | 74641d75275936796d239f828b80cb030e9f9b0a (diff) |
[MTD] [OneNAND] Use oob buffer instead of main one in oob functions
In oob functions, it is used main buffer instead of oob one. So fix it.
Signed-off-by: Kyungmin Park <kyungmin.park@samsung.com>
Signed-off-by: David Woodhouse <dwmw2@infradead.org>
Diffstat (limited to 'drivers/mtd')
-rw-r--r-- | drivers/mtd/onenand/onenand_base.c | 23 |
1 files changed, 13 insertions, 10 deletions
diff --git a/drivers/mtd/onenand/onenand_base.c b/drivers/mtd/onenand/onenand_base.c index 621c3f8ec27b..8006d51b7d27 100644 --- a/drivers/mtd/onenand/onenand_base.c +++ b/drivers/mtd/onenand/onenand_base.c | |||
@@ -1093,7 +1093,7 @@ int onenand_bbt_read_oob(struct mtd_info *mtd, loff_t from, | |||
1093 | static int onenand_verify_oob(struct mtd_info *mtd, const u_char *buf, loff_t to) | 1093 | static int onenand_verify_oob(struct mtd_info *mtd, const u_char *buf, loff_t to) |
1094 | { | 1094 | { |
1095 | struct onenand_chip *this = mtd->priv; | 1095 | struct onenand_chip *this = mtd->priv; |
1096 | char *readp = this->page_buf + mtd->writesize; | 1096 | char oobbuf[64]; |
1097 | int status, i; | 1097 | int status, i; |
1098 | 1098 | ||
1099 | this->command(mtd, ONENAND_CMD_READOOB, to, mtd->oobsize); | 1099 | this->command(mtd, ONENAND_CMD_READOOB, to, mtd->oobsize); |
@@ -1102,9 +1102,9 @@ static int onenand_verify_oob(struct mtd_info *mtd, const u_char *buf, loff_t to | |||
1102 | if (status) | 1102 | if (status) |
1103 | return status; | 1103 | return status; |
1104 | 1104 | ||
1105 | this->read_bufferram(mtd, ONENAND_SPARERAM, readp, 0, mtd->oobsize); | 1105 | this->read_bufferram(mtd, ONENAND_SPARERAM, oobbuf, 0, mtd->oobsize); |
1106 | for(i = 0; i < mtd->oobsize; i++) | 1106 | for (i = 0; i < mtd->oobsize; i++) |
1107 | if (buf[i] != 0xFF && buf[i] != readp[i]) | 1107 | if (buf[i] != 0xFF && buf[i] != oobbuf[i]) |
1108 | return -EBADMSG; | 1108 | return -EBADMSG; |
1109 | 1109 | ||
1110 | return 0; | 1110 | return 0; |
@@ -1312,6 +1312,7 @@ static int onenand_do_write_oob(struct mtd_info *mtd, loff_t to, size_t len, | |||
1312 | struct onenand_chip *this = mtd->priv; | 1312 | struct onenand_chip *this = mtd->priv; |
1313 | int column, ret = 0, oobsize; | 1313 | int column, ret = 0, oobsize; |
1314 | int written = 0; | 1314 | int written = 0; |
1315 | u_char *oobbuf; | ||
1315 | 1316 | ||
1316 | DEBUG(MTD_DEBUG_LEVEL3, "onenand_write_oob: to = 0x%08x, len = %i\n", (unsigned int) to, (int) len); | 1317 | DEBUG(MTD_DEBUG_LEVEL3, "onenand_write_oob: to = 0x%08x, len = %i\n", (unsigned int) to, (int) len); |
1317 | 1318 | ||
@@ -1331,7 +1332,7 @@ static int onenand_do_write_oob(struct mtd_info *mtd, loff_t to, size_t len, | |||
1331 | } | 1332 | } |
1332 | 1333 | ||
1333 | /* For compatibility with NAND: Do not allow write past end of page */ | 1334 | /* For compatibility with NAND: Do not allow write past end of page */ |
1334 | if (column + len > oobsize) { | 1335 | if (unlikely(column + len > oobsize)) { |
1335 | printk(KERN_ERR "onenand_write_oob: " | 1336 | printk(KERN_ERR "onenand_write_oob: " |
1336 | "Attempt to write past end of page\n"); | 1337 | "Attempt to write past end of page\n"); |
1337 | return -EINVAL; | 1338 | return -EINVAL; |
@@ -1348,6 +1349,8 @@ static int onenand_do_write_oob(struct mtd_info *mtd, loff_t to, size_t len, | |||
1348 | /* Grab the lock and see if the device is available */ | 1349 | /* Grab the lock and see if the device is available */ |
1349 | onenand_get_device(mtd, FL_WRITING); | 1350 | onenand_get_device(mtd, FL_WRITING); |
1350 | 1351 | ||
1352 | oobbuf = this->page_buf + mtd->writesize; | ||
1353 | |||
1351 | /* Loop until all data write */ | 1354 | /* Loop until all data write */ |
1352 | while (written < len) { | 1355 | while (written < len) { |
1353 | int thislen = min_t(int, oobsize, len - written); | 1356 | int thislen = min_t(int, oobsize, len - written); |
@@ -1358,12 +1361,12 @@ static int onenand_do_write_oob(struct mtd_info *mtd, loff_t to, size_t len, | |||
1358 | 1361 | ||
1359 | /* We send data to spare ram with oobsize | 1362 | /* We send data to spare ram with oobsize |
1360 | * to prevent byte access */ | 1363 | * to prevent byte access */ |
1361 | memset(this->page_buf, 0xff, mtd->oobsize); | 1364 | memset(oobbuf, 0xff, mtd->oobsize); |
1362 | if (mode == MTD_OOB_AUTO) | 1365 | if (mode == MTD_OOB_AUTO) |
1363 | onenand_fill_auto_oob(mtd, this->page_buf, buf, column, thislen); | 1366 | onenand_fill_auto_oob(mtd, oobbuf, buf, column, thislen); |
1364 | else | 1367 | else |
1365 | memcpy(this->page_buf + column, buf, thislen); | 1368 | memcpy(oobbuf + column, buf, thislen); |
1366 | this->write_bufferram(mtd, ONENAND_SPARERAM, this->page_buf, 0, mtd->oobsize); | 1369 | this->write_bufferram(mtd, ONENAND_SPARERAM, oobbuf, 0, mtd->oobsize); |
1367 | 1370 | ||
1368 | this->command(mtd, ONENAND_CMD_PROGOOB, to, mtd->oobsize); | 1371 | this->command(mtd, ONENAND_CMD_PROGOOB, to, mtd->oobsize); |
1369 | 1372 | ||
@@ -1375,7 +1378,7 @@ static int onenand_do_write_oob(struct mtd_info *mtd, loff_t to, size_t len, | |||
1375 | break; | 1378 | break; |
1376 | } | 1379 | } |
1377 | 1380 | ||
1378 | ret = onenand_verify_oob(mtd, this->page_buf, to); | 1381 | ret = onenand_verify_oob(mtd, oobbuf, to); |
1379 | if (ret) { | 1382 | if (ret) { |
1380 | printk(KERN_ERR "onenand_write_oob: verify failed %d\n", ret); | 1383 | printk(KERN_ERR "onenand_write_oob: verify failed %d\n", ret); |
1381 | break; | 1384 | break; |