pastebin

Paste #96549: Untitled ASCII paste by 90.63.216.87

diff --git a/drivers/mtd/nand/gpmi-nand/gpmi-nand.c b/drivers/mtd/nand/gpmi-nand/gpmi-nand.c
index e213d85..acc3ad4 100644
--- a/drivers/mtd/nand/gpmi-nand/gpmi-nand.c
+++ b/drivers/mtd/nand/gpmi-nand/gpmi-nand.c
@@ -1075,8 +1075,35 @@ static int gpmi_ecc_read_page(struct mtd_info *mtd, struct nand_chip *chip,
 			continue;
 
 		if (*status == STATUS_UNCORRECTABLE) {
+			int eccbits = nfc_geo->ecc_strength * nfc_geo->gf_len;
+			u8 *eccbuf = this->raw_buffer;
+			int offset, bitoffset;
+			int eccbytes;
 			int flips;
 
+			/* Read ECC bytes into our internal raw_buffer */
+			offset = ((8 * nfc_geo->ecc_chunk_size) + eccbits) * i;
+			bitoffset = offset % 8;
+			eccbytes = DIV_ROUND_UP(offset + eccbits, 8);
+			offset /= 8;
+			eccbytes -= offset;
+			chip->cmdfunc(mtd, NAND_CMD_RNDOUT, offset, -1);
+			chip->read_buf(mtd, eccbuf, eccbytes);
+
+			/*
+			 * ECC data are not byte aligned and we may have
+			 * in-band data in the first and last byte of
+			 * eccbuf. Set non-eccbits to one so that
+			 * nand_check_erased_ecc_chunk() does not count them
+			 * as bitflips.
+			 */
+			if (bitoffset)
+				eccbuf[0] |= GENMASK(bitoffset - 1, 0);
+
+			bitoffset = (bitoffset + eccbits) % 8;
+			if (bitoffset)
+				eccbuf[eccbytes - 1] |= GENMASK(7, bitoffset);
+
 			/*
 			 * The ECC hardware has an uncorrectable ECC status
 			 * code in case we have bitflips in an erased page. As
@@ -1093,7 +1120,7 @@ static int gpmi_ecc_read_page(struct mtd_info *mtd, struct nand_chip *chip,
 				flips = nand_check_erased_ecc_chunk(
 						buf + i * nfc_geo->ecc_chunk_size,
 						nfc_geo->ecc_chunk_size,
-						NULL, 0,
+						eccbuf, eccbytes,
 						auxiliary_virt,
 						nfc_geo->metadata_size,
 						nfc_geo->ecc_strength);
@@ -1101,7 +1128,7 @@ static int gpmi_ecc_read_page(struct mtd_info *mtd, struct nand_chip *chip,
 				flips = nand_check_erased_ecc_chunk(
 						buf + i * nfc_geo->ecc_chunk_size,
 						nfc_geo->ecc_chunk_size,
-						NULL, 0,
+						eccbuf, eccbytes,
 						NULL, 0,
 						nfc_geo->ecc_strength);
 			}

Private
Wrap long lines

2 + 5 =