[BUG] UBIFS corruption on powerpc 32-bit targets
Zhihao Cheng
chengzhihao1 at huawei.com
Wed Feb 4 18:14:36 PST 2026
在 2026/2/4 22:04, Tomas Alvarez Vanoli 写道:
>> Try 'fsck.ubifs -g3 -y /dev/ubi0_1'.
>
> I downloaded and cross-compiled mtd-utils for ppc, not sure if I had given
> some wrong param for configure but I was getting a segfault at
> ubifs-utils/fsck.ubifs/problem.c:236 (log_out in FILE_IS_INCONSISTENT).
>
> This is the backtrace of the crash in case you are interested (otherwise skip
> ahead to the run that worked):
>
> ```
> (gdb) bt
> #0 __GI_strlen () at ../sysdeps/powerpc/powerpc32/strlen.S:98
> #1 0x0f7ec038 in __printf_buffer (buf=buf at entry=0xbffff748,
> format=format at entry=0x1005bd38 "%s[%d] (%s%s): problem: %s, ino %lu type %s,
> nlink %u xcnt %u xsz %u xnms %u size %llu, should be nlink %u xcnt %u xsz %u
> xnms %u size %llu\n", ap=ap at entry=0xbffff838,
> mode_flags=mode_flags at entry=0) at vfprintf-process-arg.c:435
> #2 0x0f7ec608 in __vfprintf_internal (s=<optimized out>,
> format=0x1005bd38 "%s[%d] (%s%s): problem: %s, ino %lu type %s, nlink %u xcnt %u
> xsz %u xnms %u size %llu, should be nlink %u xcnt %u xsz %u xnms %u size %llu\n"
> ap=ap at entry=0xbffff838,
> mode_flags=mode_flags at entry=0) at vfprintf-internal.c:1544
> #3 0x0f7e211c in __printf (format=<optimized out>) at printf.c:33
> #4 0x1003da80 in print_problem (priv=0xbffff970, problem_type=<optimized out>,
> problem=0x10060494 <problem_table+184>, c=0x1006d2e8 <info_>) at
> ubifs-utils/fsck.ubifs/problem.c:236
> #5 fix_problem (c=c at entry=0x1006d2e8 <info_>,
> problem_type=problem_type at entry=23,
> priv=priv at entry=0xbffff9f0) at ubifs-utils/fsck.ubifs/problem.c:354
> #6 0x1003f9dc in handle_invalid_file (priv=0x0, file=0x1011c890,
> problem_type=23, c=0x1006d2e8 <info_>)
> at ubifs-utils/fsck.ubifs/extract_files.c:844
> #7 correct_file_info (file=0x1011c890, c=0x1006d2e8 <info_>)
> at ubifs-utils/fsck.ubifs/extract_files.c:1496
> #8 correct_file_info (c=0x1006d2e8 <info_>, file=0x1011c890)
> at ubifs-utils/fsck.ubifs/extract_files.c:1473
> #9 0x100439dc in check_and_correct_files (c=c at entry=0x1006d2e8 <info_>)
> at ubifs-utils/fsck.ubifs/extract_files.c:1552
> #10 0x10005f94 in do_fsck () at ubifs-utils/fsck.ubifs/fsck.ubifs.c:490
> #11 main (argc=<optimized out>, argv=<optimized out>) at
> ubifs-utils/fsck.ubifs/fsck.ubifs.c:622
> (gdb)
> ```
>
Thanks for pointing it out, Hayama has sent out the patches to fix it,
see
https://patchwork.ozlabs.org/project/linux-mtd/cover/9276ac09-7c7d-41df-9ee2-094f1c8edf93@lineo.co.jp/.
It would be appreciate that if you could modify according to the
suggestions and resend them.
> There's a warning about the formatter used for ino_t, used formatter is %lu but
> ino_t is long long unsigned int.
>
> Anyway, I split the logs into one call per value and ran it, got the following
> (patched up the log into a single line again):
>
> ```
> root at kmcent2:~# ./fsck.ubifs -y -g3 /dev/ubi1_0
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): Read superblock
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): Read master & init lpt
> <INFO> fsck.ubifs[182] (/dev/ubi1_0): ubifs_load_filesystem: recovery needed
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): Replay journal
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): Handle orphan nodes
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): Recover isize
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): Traverse TNC and construct files
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): Check and handle invalid files
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): problem: File has no inode, ino 0
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): Delete it? y
Looks like that there is only one problem, the inode cannot be found but
the dentry(ne_config.xml.gz) still exists on flash. I guess the lost
inode is 3917759 in previous log.
Maybe the inode is
UBIFS error (ubi1:0 pid 134): ubifs_iget: failed to read inode 3917759,
error -2
UBIFS error (ubi1:0 pid 134): ubifs_lookup: dead directory entry
'ne_config.xml.gz', error -2
UBIFS warning (ubi1:0 pid 134): ubifs_ro_mode: switched to read-only
mode, error -2
find: /cfg/board/cfg/mob/backup/ne/ne_config.xml.gz: No such fiCPU: 1
UID: 0 PID: 134 Comm: find Not tainted 6.12.57-00435-gf9e139970f1f #0
Apply following patch to kernel and mount bad ubifs image, let's try to
find more information after a full volume scanning:
diff --git a/fs/ubifs/super.c b/fs/ubifs/super.c
index f453c37cee37..35d54e1a7ecd 100644
--- a/fs/ubifs/super.c
+++ b/fs/ubifs/super.c
@@ -1491,6 +1491,89 @@ static int mount_ubifs(struct ubifs_info *c)
} else
ubifs_assert(c, c->lst.taken_empty_lebs > 0);
+ int lnum, len, ret, offs;
+ char *leb_buf, *buf;
+
+ leb_buf = vmalloc(c->leb_size);
+ if (!leb_buf)
+ return -ENOMEM;
+
+ for (lnum = c->main_first; lnum < c->leb_cnt; ++lnum) {
+ pr_info("---------- Start scan LEB %d (main_first %d) ----------\n",
lnum, c->main_first);
+ ubifs_leb_read(c, lnum, leb_buf, 0, c->leb_size, 0);
+ //print_hex_dump(KERN_INFO, "", DUMP_PREFIX_OFFSET, 32, 1, (void
*)leb_buf, c->leb_size, 1);
+ len = c->leb_size;
+ buf = leb_buf;
+ offs = 0;
+
+ while (len >= 8) {
+ int found;
+ int node_len;
+ struct ubifs_ch *ch = (struct ubifs_ch *)buf;
+ struct ubifs_ino_node *ino;
+ struct ubifs_dent_node *dent;
+ struct ubifs_data_node *dn;
+ union ubifs_key key;
+
+ ret = ubifs_scan_a_node(c, buf, len, lnum, offs, 0);
+ if (ret > 0) {
+ pr_info("padding bytes %d:%d\n", offs, offs + ret);
+ offs += ret;
+ buf += ret;
+ len -= ret;
+ continue;
+ }
+ if (ret == SCANNED_EMPTY_SPACE) {
+ break;
+ } else if (ret != SCANNED_A_NODE) {
+ ubifs_err(c, "SCAN ret = %d", ret);
+ break;
+ }
+
+ node_len = ALIGN(le32_to_cpu(ch->len), 8);
+
+ switch (ch->node_type) {
+ case UBIFS_INO_NODE:
+ ino = (struct ubifs_ino_node *)buf;
+ key_read(c, &ino->key, &key);
+
+ found = ubifs_tnc_has_node(c, &key, 0, lnum, offs, 0);
+ pr_info("ino %u found %d %d-%d\n", key.u32[0], found, offs, offs +
node_len);
+ break;
+ case UBIFS_DENT_NODE:
+ dent = (struct ubifs_dent_node *)buf;
+ key_read(c, &dent->key, &key);
+
+ found = ubifs_tnc_has_node(c, &key, 0, lnum, offs, 0);
+ pr_info("dent %llu(%s) found %d %d-%d\n", dent->inum, dent->name,
found, offs, offs + node_len);
+ break;
+ case UBIFS_DATA_NODE:
+ dn = (struct ubifs_data_node *)buf;
+ key_read(c, &dn->key, &key);
+
+ found = ubifs_tnc_has_node(c, &key, 0, lnum, offs, 0);
+ pr_info("data %u found %d %d-%d\n", key.u32[0], found, offs, offs +
node_len);
+ break;
+ default:
+ pr_info("unknown type %d\n", ch->node_type);
+ break;
+ }
+
+ offs += node_len;
+ buf += node_len;
+ len -= node_len;
+ }
+
+ for (; len > 4; offs += 4, buf += 4, len -= 4)
+ if (*(uint32_t *)buf != 0xffffffff)
+ break;
+ for (; len; offs++, buf++, len--)
+ if (*(uint8_t *)buf != 0xff)
+ ubifs_err(c, "corrupt empty space at LEB %d:%d", lnum, offs);
+ }
+
+ pr_info("============ FINISH ==========\n");
+
err = dbg_check_filesystem(c);
if (err)
goto out_infos;
>
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): Check and handle unreachable files
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): Check and correct files
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): problem: File is inconsistent ino
> 184322 type dir nlink 2 xcnt 0 xsz 0 xnms 0 size 472, should be nlink 2 xcnt 0
> xsz 0 xnms 0 size 392
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): Fix it? y
>
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): Check whether the TNC is empty
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): Check and correct the space
> statistics
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): Commit problem fixing modifications
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): Check and correct the index size
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): Check and create root dir
> fsck.ubifs[182] (/dev/ubi1_0,danger mode): Final committing
> fsck.ubifs[182] (-): ********** Filesystem was modified **********
> fsck.ubifs[182] (-): FSCK success!
> root at kmcent2:~#
> ```
>
> Seems potentially the size of the node was wrong?
> After the run, the fs is, as expected, not broken anymore.
>
>
> PS: my email client might be omitting the in-reply-to headers, sorry about that
>
> Best regards,
> Tomas
>
>
> .
>
More information about the linux-mtd
mailing list