aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorIvan Djelic2012-04-17 13:11:53 +0200
committerDavid Woodhouse2012-05-13 22:54:00 -0500
commita9c465f07c2dcd515d20b96f93470762f9ae08b6 (patch)
tree032b37acddd9c54b34adfdc3acf03a48a30e0453
parente25da1c07dfb318628a8a86f0967914dc4fd135e (diff)
mtd: nand: omap: fix race condition in omap_wait()
If a context switch occurs in function omap_wait() just before the while loop is entered, then upon return from context switch the timeout may already have elapsed: in that case, status is never read from NAND device, and omap_wait() returns an error. This failure has been experimentally observed during stress tests. This patch ensures a NAND status read is always performed before returning, as in the generic nand_wait() function. Signed-off-by: Ivan Djelic <ivan.djelic@parrot.com> Signed-off-by: Artem Bityutskiy <Artem.Bityutskiy@linux.intel.com> Signed-off-by: David Woodhouse <David.Woodhouse@intel.com>
-rw-r--r--drivers/mtd/nand/omap2.c4
1 files changed, 3 insertions, 1 deletions
diff --git a/drivers/mtd/nand/omap2.c b/drivers/mtd/nand/omap2.c
index ab56069fa31f..05d3562ec748 100644
--- a/drivers/mtd/nand/omap2.c
+++ b/drivers/mtd/nand/omap2.c
@@ -881,7 +881,7 @@ static int omap_wait(struct mtd_info *mtd, struct nand_chip *chip)
struct omap_nand_info *info = container_of(mtd, struct omap_nand_info,
mtd);
unsigned long timeo = jiffies;
- int status = NAND_STATUS_FAIL, state = this->state;
+ int status, state = this->state;
if (state == FL_ERASING)
timeo += (HZ * 400) / 1000;
@@ -896,6 +896,8 @@ static int omap_wait(struct mtd_info *mtd, struct nand_chip *chip)
break;
cond_resched();
}
+
+ status = gpmc_nand_read(info->gpmc_cs, GPMC_NAND_DATA);
return status;
}