From 248ae5cfc8bf69074d1da099dc495d8e06070547 Mon Sep 17 00:00:00 2001 From: Sergei Poselenov Date: Fri, 6 Jun 2008 15:42:43 +0200 Subject: [PATCH] NAND: Added support for 128-bit OOB, adapted Signed-off-by: Sergei Poselenov --- drivers/mtd/nand/nand_base.c | 46 ++++++++++++++++++++++++++---------- include/linux/mtd/mtd-abi.h | 2 +- 2 files changed, 34 insertions(+), 14 deletions(-) diff --git a/drivers/mtd/nand/nand_base.c b/drivers/mtd/nand/nand_base.c index 5aef31cd18..740d3fcc37 100644 --- a/drivers/mtd/nand/nand_base.c +++ b/drivers/mtd/nand/nand_base.c @@ -113,18 +113,22 @@ static struct nand_oobinfo nand_oob_64 = { .oobfree = { {2, 38} } }; -/* This is used for padding purposes in nand_write_oob */ -static u_char ffchars[] = { - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, +static struct nand_oobinfo nand_oob_128 = { + .useecc = MTD_NANDECC_AUTOPLACE, + .eccbytes = 48, + .eccpos = { + 80, 81, 82, 83, 84, 85, 86, 87, + 88, 89, 90, 91, 92, 93, 94, 95, + 96, 97, 98, 99, 100, 101, 102, 103, + 104, 105, 106, 107, 108, 109, 110, 111, + 112, 113, 114, 115, 116, 117, 118, 119, + 120, 121, 122, 123, 124, 125, 126, 127}, + .oobfree = { {2, 78} } }; +/* This is used for padding purposes in nand_write_oob */ +static u_char *ffchars; + /* * NAND low-level MTD interface functions */ @@ -193,6 +197,10 @@ static void nand_release_device (struct mtd_info *mtd) { struct nand_chip *this = mtd->priv; this->select_chip(mtd, -1); /* De-select the NAND device */ + if (ffchars) { + kfree(ffchars); + ffchars = NULL; + } } #endif @@ -891,7 +899,7 @@ static int nand_write_page (struct mtd_info *mtd, struct nand_chip *this, int pa u_char *oob_buf, struct nand_oobinfo *oobsel, int cached) { int i, status; - u_char ecc_code[32]; + u_char ecc_code[NAND_MAX_OOBSIZE]; int eccmode = oobsel->useecc ? this->eccmode : NAND_ECC_NONE; uint *oob_config = oobsel->eccpos; int datidx = 0, eccidx = 0, eccsteps = this->eccsteps; @@ -1112,8 +1120,8 @@ static int nand_read_ecc (struct mtd_info *mtd, loff_t from, size_t len, int read = 0, oob = 0, ecc_status = 0, ecc_failed = 0; struct nand_chip *this = mtd->priv; u_char *data_poi, *oob_data = oob_buf; - u_char ecc_calc[32]; - u_char ecc_code[32]; + u_char ecc_calc[NAND_MAX_OOBSIZE]; + u_char ecc_code[NAND_MAX_OOBSIZE]; int eccmode, eccsteps; unsigned *oob_config; int datidx; @@ -1811,6 +1819,15 @@ static int nand_write_oob (struct mtd_info *mtd, loff_t to, size_t len, size_t * if (NAND_MUST_PAD(this)) { /* Write out desired data */ this->cmdfunc (mtd, NAND_CMD_SEQIN, mtd->oobblock, page & this->pagemask); + if (!ffchars) { + if (!(ffchars = kmalloc (mtd->oobsize, GFP_KERNEL))) { + DEBUG (MTD_DEBUG_LEVEL0, "nand_write_oob: " + "No memory for padding array, need %d bytes", mtd->oobsize); + ret = -ENOMEM; + goto out; + } + memset(ffchars, 0xff, mtd->oobsize); + } /* prepad 0xff for partial programming */ this->write_buf(mtd, ffchars, column); /* write data */ @@ -2479,6 +2496,9 @@ int nand_scan (struct mtd_info *mtd, int maxchips) case 64: this->autooob = &nand_oob_64; break; + case 128: + this->autooob = &nand_oob_128; + break; default: printk (KERN_WARNING "No oob scheme defined for oobsize %d\n", mtd->oobsize); diff --git a/include/linux/mtd/mtd-abi.h b/include/linux/mtd/mtd-abi.h index 72d7341d75..4cebea9597 100644 --- a/include/linux/mtd/mtd-abi.h +++ b/include/linux/mtd/mtd-abi.h @@ -93,7 +93,7 @@ struct nand_oobinfo { uint32_t useecc; uint32_t eccbytes; uint32_t oobfree[8][2]; - uint32_t eccpos[32]; + uint32_t eccpos[48]; }; #endif /* __MTD_ABI_H__ */ -- 2.25.1