[<prev] [next>] [thread-next>] [day] [month] [year] [list]
Message-ID: <20250818164635573BQolnx5DcBqRicqxF0DMl@zte.com.cn>
Date: Mon, 18 Aug 2025 16:46:35 +0800 (CST)
From: <shao.mingyin@....com.cn>
To: <chengzhihao1@...wei.com>
Cc: <linux-mtd@...ts.infradead.org>, <linux-kernel@...r.kernel.org>,
<yang.yang29@....com.cn>, <xu.xin16@....com.cn>,
<yang.tao172@....com.cn>, <richard@....at>
Subject: [PATCH] ubifs: address bit flips in unused free space
From: Shao Mingyin <shao.mingyin@....com.cn>
When the recovery detects a free space bit flip, the UBIFS mount fails,
rendering the UBIFS unusable. This issue can be addressed by reclaiming
the affected erase block, which involves relocating its valid data. So
attempting to fix free space bit flip during recovery reduces scenarios
where users cannot access UBIFS normally.
Signed-off-by: Shao Mingyin <shao.mingyin@....com.cn>
Signed-off-by: yang tao <yang.tao172@....com.cn>
---
fs/ubifs/recovery.c | 25 +++++++++++++++++++++++++
1 file changed, 25 insertions(+)
diff --git a/fs/ubifs/recovery.c b/fs/ubifs/recovery.c
index f0d51dd21c9e..cebf4098557c 100644
--- a/fs/ubifs/recovery.c
+++ b/fs/ubifs/recovery.c
@@ -77,6 +77,25 @@ static int first_non_ff(void *buf, int len)
return -1;
}
+static int ubifs_buf_bitflip_count(void *buf, int len)
+{
+ uint8_t tmp, shift;
+ uint8_t *p = buf;
+ int i, count = 0;
+
+ for (i = 0; i < len; i++) {
+ tmp = *p++;
+ if (tmp != 0xff) {
+ shift = (uint8_t)0;
+ while (shift <= 7)
+ if (!(tmp & (uint8_t)(1 << shift++)))
+ count++;
+ }
+ }
+
+ return count;
+}
+
/**
* get_master_node - get the last valid master node allowing for corruption.
* @c: UBIFS file-system description object
@@ -690,6 +709,12 @@ struct ubifs_scan_leb *ubifs_recover_leb(struct ubifs_info *c, int lnum,
* See header comment for this file for more
* explanations about the reasons we have this check.
*/
+ int bitflip_count = ubifs_buf_bitflip_count(buf, len);
+
+ ubifs_assert(c, bitflip_count > 0);
+ ubifs_msg(c, "corrupt empty space LEB %d:%d, corruption starts at %d, bitflip count %d, try to rescure",
+ lnum, offs, corruption, bitflip_count);
+ goto rescure;
ubifs_err(c, "corrupt empty space LEB %d:%d, corruption starts at %d",
lnum, offs, corruption);
/* Make sure we dump interesting non-0xFF data */
@@ -766,6 +790,7 @@ struct ubifs_scan_leb *ubifs_recover_leb(struct ubifs_info *c, int lnum,
len = c->leb_size - offs;
clean_buf(c, &buf, lnum, &offs, &len);
+rescure:
ubifs_end_scan(c, sleb, lnum, offs);
err = fix_unclean_leb(c, sleb, start);
--
2.25.1
Powered by blists - more mailing lists