aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/mtd/ubi/build.c
diff options
context:
space:
mode:
authorArtem Bityutskiy <Artem.Bityutskiy@nokia.com>2010-09-03 16:08:15 -0400
committerArtem Bityutskiy <Artem.Bityutskiy@nokia.com>2010-10-19 10:19:57 -0400
commit5fc01ab6934c43b42c41bc753fe1123c16d7f38f (patch)
tree174a1e1a0d283ec8ca4c756d7f354a475ac46a36 /drivers/mtd/ubi/build.c
parentfeeba4b872e5166ca64c44fbb5bbec234dfce199 (diff)
UBI: preserve corrupted PEBs
Currently UBI erases all corrupted eraseblocks, irrespectively of the nature of corruption: corruption due to power cuts and non-power cut corruption. The former case is OK, but the latter is not, because UBI may destroy potentially important data. With this patch, during scanning, when UBI hits a PEB with corrupted VID header, it checks whether this PEB contains only 0xFF data. If yes, it is safe to erase this PEB and it is put to the 'erase' list. If not, this may be important data and it is better to avoid erasing this PEB. Instead, UBI puts it to the corr list and moves out of the pool of available PEB. IOW, UBI preserves this PEB. Such corrupted PEB lessen the amount of available PEBs. So the more of them we accumulate, the less PEBs are available. The maximum amount of non-power cut corrupted PEBs is 8. This patch is a response to UBIFS problem where reporter (Matthew L. Creech <mlcreech@gmail.com>) observes that UBIFS index points to an unmapped LEB. The theory is that corresponding PEB somehow got corrupted and UBI wiped it. This patch (actually a series of patches) tries to make sure such PEBs are preserved - this would make it is easier to analyze the corruption. Signed-off-by: Artem Bityutskiy <Artem.Bityutskiy@nokia.com>
Diffstat (limited to 'drivers/mtd/ubi/build.c')
-rw-r--r--drivers/mtd/ubi/build.c2
1 files changed, 2 insertions, 0 deletions
diff --git a/drivers/mtd/ubi/build.c b/drivers/mtd/ubi/build.c
index f247c4e7b40d..5ebe280225d6 100644
--- a/drivers/mtd/ubi/build.c
+++ b/drivers/mtd/ubi/build.c
@@ -591,6 +591,7 @@ static int attach_by_scanning(struct ubi_device *ubi)
591 591
592 ubi->bad_peb_count = si->bad_peb_count; 592 ubi->bad_peb_count = si->bad_peb_count;
593 ubi->good_peb_count = ubi->peb_count - ubi->bad_peb_count; 593 ubi->good_peb_count = ubi->peb_count - ubi->bad_peb_count;
594 ubi->corr_peb_count = si->corr_peb_count;
594 ubi->max_ec = si->max_ec; 595 ubi->max_ec = si->max_ec;
595 ubi->mean_ec = si->mean_ec; 596 ubi->mean_ec = si->mean_ec;
596 ubi_msg("max. sequence number: %llu", si->max_sqnum); 597 ubi_msg("max. sequence number: %llu", si->max_sqnum);
@@ -972,6 +973,7 @@ int ubi_attach_mtd_dev(struct mtd_info *mtd, int ubi_num, int vid_hdr_offset)
972 ubi_msg("MTD device size: %llu MiB", ubi->flash_size >> 20); 973 ubi_msg("MTD device size: %llu MiB", ubi->flash_size >> 20);
973 ubi_msg("number of good PEBs: %d", ubi->good_peb_count); 974 ubi_msg("number of good PEBs: %d", ubi->good_peb_count);
974 ubi_msg("number of bad PEBs: %d", ubi->bad_peb_count); 975 ubi_msg("number of bad PEBs: %d", ubi->bad_peb_count);
976 ubi_msg("number of corrupted PEBs: %d", ubi->corr_peb_count);
975 ubi_msg("max. allowed volumes: %d", ubi->vtbl_slots); 977 ubi_msg("max. allowed volumes: %d", ubi->vtbl_slots);
976 ubi_msg("wear-leveling threshold: %d", CONFIG_MTD_UBI_WL_THRESHOLD); 978 ubi_msg("wear-leveling threshold: %d", CONFIG_MTD_UBI_WL_THRESHOLD);
977 ubi_msg("number of internal volumes: %d", UBI_INT_VOL_COUNT); 979 ubi_msg("number of internal volumes: %d", UBI_INT_VOL_COUNT);