[U-Boot] [PATCH V2 2/4] mtd/NAND: Add FSMC driver support

Amit Virdi amit.virdi at st.com
Wed May 16 13:05:56 CEST 2012


On 5/16/2012 2:44 AM, Scott Wood wrote:
>> +    case FSMC_VER8:
>> +        /* Busy waiting for ecc computation to finish for 512 bytes */
>> +        while (!(readl(&fsmc_regs_p->sts)&  FSMC_CODE_RDY))
>> +            ;
>
> Timeout?
>

>> +    uint16_t ecc_oob[7];
>> +    uint8_t *oob = (uint8_t *)&ecc_oob[0];
>
> Please use a union, or better an explicit alignment attribute.
>

>> +enum {
>> +    FSMC_VER1 = 1,
>> +    FSMC_VER2,
>> +    FSMC_VER3,
>> +    FSMC_VER4,
>> +    FSMC_VER5,
>> +    FSMC_VER6,
>> +    FSMC_VER7,
>> +    FSMC_VER8,
>> +};
>
> Is this really necessary?
>

Three fixups.

Signed-off-by: Amit Virdi <amit.virdi at st.com>
---
 drivers/mtd/nand/fsmc_nand.c  |   24 +++++++++++++-----------
 include/linux/mtd/fsmc_nand.h |   12 ++----------
 2 files changed, 15 insertions(+), 21 deletions(-)

diff --git a/drivers/mtd/nand/fsmc_nand.c b/drivers/mtd/nand/fsmc_nand.c
index 5e91ece..f38603a 100644
--- a/drivers/mtd/nand/fsmc_nand.c
+++ b/drivers/mtd/nand/fsmc_nand.c
@@ -278,12 +278,20 @@ static int fsmc_read_hwecc(struct mtd_info *mtd,
 			const u_char *data, u_char *ecc)
 {
 	u_int ecc_tmp;
+	int timeout = FSMC_CODE_RDY_TIMEOUT;
+	ulong start;
 
 	switch (fsmc_version) {
 	case FSMC_VER8:
-		/* Busy waiting for ecc computation to finish for 512 bytes */
-		while (!(readl(&fsmc_regs_p->sts) & FSMC_CODE_RDY))
-			;
+		start = get_timer(0);
+		while (get_timer(start) < timeout) {
+			/*
+			 * Busy waiting for ecc computation
+			 * to finish for 512 bytes
+			 */
+			if (readl(&fsmc_regs_p->sts) & FSMC_CODE_RDY)
+				break;
+		}
 
 		ecc_tmp = readl(&fsmc_regs_p->ecc1);
 		ecc[0] = (u_char) (ecc_tmp >> 0);
@@ -352,13 +360,7 @@ static int fsmc_read_page_hwecc(struct mtd_info *mtd, struct nand_chip *chip,
 	uint8_t *ecc_calc = chip->buffers->ecccalc;
 	uint8_t *ecc_code = chip->buffers->ecccode;
 	int off, len, group = 0;
-	/*
-	 * ecc_oob is intentionally taken as u16. In 16bit devices, we end up
-	 * reading 14 bytes (7 words) from oob. The local array is to maintain
-	 * word alignment
-	 */
-	uint16_t ecc_oob[7];
-	uint8_t *oob = (uint8_t *)&ecc_oob[0];
+	uint8_t oob[13] __attribute__ ((aligned (16)));
 
 	/* Differentiate between small and large page ecc place definitions */
 	if (mtd->writesize == 512)
@@ -389,7 +391,7 @@ static int fsmc_read_page_hwecc(struct mtd_info *mtd, struct nand_chip *chip,
 			j += len;
 		}
 
-		memcpy(&ecc_code[i], ecc_oob, 13);
+		memcpy(&ecc_code[i], oob, 13);
 		chip->ecc.calculate(mtd, p, &ecc_calc[i]);
 
 		stat = chip->ecc.correct(mtd, p, &ecc_code[i],
diff --git a/include/linux/mtd/fsmc_nand.h b/include/linux/mtd/fsmc_nand.h
index 3bd8fc0..efc6eb3 100644
--- a/include/linux/mtd/fsmc_nand.h
+++ b/include/linux/mtd/fsmc_nand.h
@@ -77,16 +77,8 @@ struct fsmc_regs {
 #define FSMC_REVISION_MSK	(0xf)
 #define FSMC_REVISION_SHFT	(0x4)
 
-enum {
-	FSMC_VER1 = 1,
-	FSMC_VER2,
-	FSMC_VER3,
-	FSMC_VER4,
-	FSMC_VER5,
-	FSMC_VER6,
-	FSMC_VER7,
-	FSMC_VER8,
-};
+#define FSMC_CODE_RDY_TIMEOUT	1000	/* 1 sec */
+#define FSMC_VER8		0x8
 
 /*
  * There are 13 bytes of ecc for every 512 byte block and it has to be read
-- 
1.7.2.2



More information about the U-Boot mailing list