[MTD] RFD FTL: Be noisier, and don't assume block without RFD magic are erased

Linux-MTD Mailing List linux-mtd at lists.infradead.org
Wed May 17 07:59:02 EDT 2006


Commit:     683b30c8e78ab363dc8d8c94bdb61b64d1f6f5e2
Parent:     ae282d497d5631ce31539717131c760e3872c539
Author:     Sean Young <sean at mess.org>
AuthorDate: Wed May 17 12:45:34 2006 +0100
Commit:     David Woodhouse <dwmw2 at infradead.org>
CommitDate: Wed May 17 12:45:34 2006 +0100

    [MTD] RFD FTL: Be noisier, and don't assume block without RFD magic are erased
    
    Signed-off-by: Sean Young <sean at mess.org>
    Signed-off-by: David Woodhouse <dwmw2 at infradead.org>

 drivers/mtd/rfd_ftl.c |   48 +++++++++++++++++++++++++-----------------------
 1 files changed, 25 insertions(+), 23 deletions(-)

diff --git a/drivers/mtd/rfd_ftl.c b/drivers/mtd/rfd_ftl.c
index a3e00a4..fa4362f 100644
--- a/drivers/mtd/rfd_ftl.c
+++ b/drivers/mtd/rfd_ftl.c
@@ -3,7 +3,7 @@
  *
  * Copyright (C) 2005  Sean Young <sean at mess.org>
  *
- * $Id: rfd_ftl.c,v 1.5 2005/11/07 11:14:21 gleixner Exp $
+ * $Id: rfd_ftl.c,v 1.8 2006/01/15 12:51:44 sean Exp $
  *
  * This type of flash translation layer (FTL) is used by the Embedded BIOS
  * by General Software. It is known as the Resident Flash Disk (RFD), see:
@@ -61,6 +61,7 @@ struct block {
 		BLOCK_OK,
 		BLOCK_ERASING,
 		BLOCK_ERASED,
+		BLOCK_UNUSED,
 		BLOCK_FAILED
 	} state;
 	int free_sectors;
@@ -99,10 +100,8 @@ static int build_block_map(struct partit
 	block->offset = part->block_size * block_no;
 
 	if (le16_to_cpu(part->header_cache[0]) != RFD_MAGIC) {
-		block->state = BLOCK_ERASED; /* assumption */
-		block->free_sectors = part->data_sectors_per_block;
-		part->reserved_block = block_no;
-		return 1;
+		block->state = BLOCK_UNUSED;
+		return -ENOENT;
 	}
 
 	block->state = BLOCK_OK;
@@ -124,7 +123,7 @@ static int build_block_map(struct partit
 			entry = 0;
 
 		if (entry >= part->sector_count) {
-			printk(KERN_NOTICE PREFIX
+			printk(KERN_WARNING PREFIX
 				"'%s': unit #%d: entry %d corrupt, "
 				"sector %d out of range\n",
 				part->mbd.mtd->name, block_no, i, entry);
@@ -132,7 +131,7 @@ static int build_block_map(struct partit
 		}
 
 		if (part->sector_map[entry] != -1) {
-			printk(KERN_NOTICE PREFIX
+			printk(KERN_WARNING PREFIX
 				"'%s': more than one entry for sector %d\n",
 				part->mbd.mtd->name, entry);
 			part->errors = 1;
@@ -167,7 +166,7 @@ static int scan_header(struct partition 
 	/* each erase block has three bytes header, followed by the map */
 	part->header_sectors_per_block =
 			((HEADER_MAP_OFFSET + sectors_per_block) *
-		 	sizeof(u16) + SECTOR_SIZE - 1) / SECTOR_SIZE;
+			sizeof(u16) + SECTOR_SIZE - 1) / SECTOR_SIZE;
 
 	part->data_sectors_per_block = sectors_per_block -
 			part->header_sectors_per_block;
@@ -226,7 +225,7 @@ static int scan_header(struct partition 
 	}
 
 	if (part->reserved_block == -1) {
-		printk(KERN_NOTICE PREFIX "'%s': no empty erase unit found\n",
+		printk(KERN_WARNING PREFIX "'%s': no empty erase unit found\n",
 				part->mbd.mtd->name);
 
 		part->errors = 1;
@@ -315,7 +314,7 @@ static void erase_callback(struct erase_
 		rc = -EIO;
 
 	if (rc) {
-		printk(KERN_NOTICE PREFIX "'%s': unable to write RFD "
+		printk(KERN_ERR PREFIX "'%s': unable to write RFD "
 				"header at 0x%lx\n",
 				part->mbd.mtd->name,
 				part->blocks[i].offset);
@@ -348,7 +347,7 @@ static int erase_block(struct partition 
 	rc = part->mbd.mtd->erase(part->mbd.mtd, erase);
 
 	if (rc) {
-		printk(KERN_WARNING PREFIX "erase of region %x,%x on '%s' "
+		printk(KERN_ERR PREFIX "erase of region %x,%x on '%s' "
 				"failed\n", erase->addr, erase->len,
 				part->mbd.mtd->name);
 		kfree(erase);
@@ -383,7 +382,7 @@ static int move_block_contents(struct pa
 		rc = -EIO;
 
 	if (rc) {
-		printk(KERN_NOTICE PREFIX "error reading '%s' at "
+		printk(KERN_ERR PREFIX "error reading '%s' at "
 			"0x%lx\n", part->mbd.mtd->name,
 			part->blocks[block_no].offset);
 
@@ -423,7 +422,7 @@ static int move_block_contents(struct pa
 			rc = -EIO;
 
 		if (rc) {
-			printk(KERN_NOTICE PREFIX "'%s': Unable to "
+			printk(KERN_ERR PREFIX "'%s': Unable to "
 				"read sector for relocation\n",
 				part->mbd.mtd->name);
 
@@ -520,7 +519,7 @@ static int reclaim_block(struct partitio
  * because if we fill that one up first it'll have the most chance of having
  * the least live sectors at reclaim.
  */
-static int find_free_block(const struct partition *part)
+static int find_free_block(struct partition *part)
 {
 	int block, stop;
 
@@ -533,6 +532,9 @@ static int find_free_block(const struct 
 				block != part->reserved_block)
 			return block;
 
+		if (part->blocks[block].state == BLOCK_UNUSED)
+			erase_block(part, block);
+
 		if (++block >= part->total_blocks)
 			block = 0;
 
@@ -541,7 +543,7 @@ static int find_free_block(const struct 
 	return -1;
 }
 
-static int find_writeable_block(struct partition *part, u_long *old_sector)
+static int find_writable_block(struct partition *part, u_long *old_sector)
 {
 	int rc, block;
 	size_t retlen;
@@ -570,7 +572,7 @@ static int find_writeable_block(struct p
 		rc = -EIO;
 
 	if (rc) {
-		printk(KERN_NOTICE PREFIX "'%s': unable to read header at "
+		printk(KERN_ERR PREFIX "'%s': unable to read header at "
 				"0x%lx\n", part->mbd.mtd->name,
 				part->blocks[block].offset);
 		goto err;
@@ -602,7 +604,7 @@ static int mark_sector_deleted(struct pa
 		rc = -EIO;
 
 	if (rc) {
-		printk(KERN_WARNING PREFIX "error writing '%s' at "
+		printk(KERN_ERR PREFIX "error writing '%s' at "
 			"0x%lx\n", part->mbd.mtd->name, addr);
 		if (rc)
 			goto err;
@@ -652,7 +654,7 @@ static int do_writesect(struct mtd_blktr
 	if (part->current_block == -1 ||
 		!part->blocks[part->current_block].free_sectors) {
 
-		rc = find_writeable_block(part, old_addr);
+		rc = find_writable_block(part, old_addr);
 		if (rc)
 			goto err;
 	}
@@ -675,7 +677,7 @@ static int do_writesect(struct mtd_blktr
 		rc = -EIO;
 
 	if (rc) {
-		printk(KERN_WARNING PREFIX "error writing '%s' at 0x%lx\n",
+		printk(KERN_ERR PREFIX "error writing '%s' at 0x%lx\n",
 				part->mbd.mtd->name, addr);
 		if (rc)
 			goto err;
@@ -695,7 +697,7 @@ static int do_writesect(struct mtd_blktr
 		rc = -EIO;
 
 	if (rc) {
-		printk(KERN_WARNING PREFIX "error writing '%s' at 0x%lx\n",
+		printk(KERN_ERR PREFIX "error writing '%s' at 0x%lx\n",
 				part->mbd.mtd->name, addr);
 		if (rc)
 			goto err;
@@ -776,7 +778,7 @@ static void rfd_ftl_add_mtd(struct mtd_b
 		part->block_size = block_size;
 	else {
 		if (!mtd->erasesize) {
-			printk(KERN_NOTICE PREFIX "please provide block_size");
+			printk(KERN_WARNING PREFIX "please provide block_size");
 			return;
 		}
 		else
@@ -791,8 +793,8 @@ static void rfd_ftl_add_mtd(struct mtd_b
 		if (!(mtd->flags & MTD_WRITEABLE))
 			part->mbd.readonly = 1;
 		else if (part->errors) {
-			printk(KERN_NOTICE PREFIX "'%s': errors found, "
-					"setting read-only", mtd->name);
+			printk(KERN_WARNING PREFIX "'%s': errors found, "
+					"setting read-only\n", mtd->name);
 			part->mbd.readonly = 1;
 		}
 



More information about the linux-mtd-cvs mailing list