From 96a8afa7c134ef9239a70f264c35e709737f42cd Mon Sep 17 00:00:00 2001 From: Theodore Ts'o Date: Wed, 28 Sep 2011 15:12:55 -0400 Subject: [PATCH] e2fsck: check for invalid bad block inode In some cases the bad block inode gets corrupted. If it looks insane, offer to clear it before trying to interpret it does more harm than good. Signed-off-by: "Theodore Ts'o" --- e2fsck/pass1.c | 11 +++++++++++ e2fsck/problem.c | 5 +++++ e2fsck/problem.h | 3 +++ tests/f_invalid_bad_inode/expect.1 | 11 +++++++++++ tests/f_invalid_bad_inode/expect.2 | 7 +++++++ tests/f_invalid_bad_inode/image.gz | Bin 0 -> 623 bytes tests/f_invalid_bad_inode/name | 1 + 7 files changed, 38 insertions(+) create mode 100644 tests/f_invalid_bad_inode/expect.1 create mode 100644 tests/f_invalid_bad_inode/expect.2 create mode 100644 tests/f_invalid_bad_inode/image.gz create mode 100644 tests/f_invalid_bad_inode/name diff --git a/e2fsck/pass1.c b/e2fsck/pass1.c index f45831fa..7ce66979 100644 --- a/e2fsck/pass1.c +++ b/e2fsck/pass1.c @@ -821,6 +821,14 @@ void e2fsck_pass1(e2fsck_t ctx) if (ino == EXT2_BAD_INO) { struct process_block_struct pb; + if ((inode->i_mode || inode->i_uid || inode->i_gid || + inode->i_links_count || inode->i_file_acl) && + fix_problem(ctx, PR_1_INVALID_BAD_INODE, &pctx)) { + memset(inode, 0, sizeof(struct ext2_inode)); + e2fsck_write_inode(ctx, ino, inode, + "clear bad inode"); + } + pctx.errcode = ext2fs_copy_bitmap(ctx->block_found_map, &pb.fs_meta_blocks); if (pctx.errcode) { @@ -1715,6 +1723,9 @@ void e2fsck_clear_inode(e2fsck_t ctx, ext2_ino_t ino, */ ctx->flags |= restart_flag; + if (ino == EXT2_BAD_INO) + memset(inode, 0, sizeof(struct ext2_inode)); + e2fsck_write_inode(ctx, ino, inode, source); } diff --git a/e2fsck/problem.c b/e2fsck/problem.c index cf4a270b..6ee3fa4f 100644 --- a/e2fsck/problem.c +++ b/e2fsck/problem.c @@ -936,6 +936,11 @@ static struct e2fsck_problem problem_table[] = { N_("@q @i is visible to the user. "), PROMPT_CLEAR, PR_PREEN_OK }, + /* Invalid bad inode */ + { PR_1_INVALID_BAD_INODE, + N_("The bad @b @i looks @n. "), + PROMPT_CLEAR, 0 }, + /* Pass 1b errors */ /* Pass 1B: Rescan for duplicate/bad blocks */ diff --git a/e2fsck/problem.h b/e2fsck/problem.h index 17b0c106..9db29d80 100644 --- a/e2fsck/problem.h +++ b/e2fsck/problem.h @@ -547,6 +547,9 @@ struct problem_context { /* Quota inode is user visible */ #define PR_1_QUOTA_INODE_NOT_HIDDEN 0x010064 +/* Invalid bad inode */ +#define PR_1_INVALID_BAD_INODE 0x010065 + /* * Pass 1b errors */ diff --git a/tests/f_invalid_bad_inode/expect.1 b/tests/f_invalid_bad_inode/expect.1 new file mode 100644 index 00000000..5a37cb07 --- /dev/null +++ b/tests/f_invalid_bad_inode/expect.1 @@ -0,0 +1,11 @@ +Pass 1: Checking inodes, blocks, and sizes +The bad block inode looks invalid. Clear? yes + +Pass 2: Checking directory structure +Pass 3: Checking directory connectivity +Pass 4: Checking reference counts +Pass 5: Checking group summary information + +test_filesys: ***** FILE SYSTEM WAS MODIFIED ***** +test_filesys: 11/16 files (0.0% non-contiguous), 21/100 blocks +Exit status is 1 diff --git a/tests/f_invalid_bad_inode/expect.2 b/tests/f_invalid_bad_inode/expect.2 new file mode 100644 index 00000000..41ceefb4 --- /dev/null +++ b/tests/f_invalid_bad_inode/expect.2 @@ -0,0 +1,7 @@ +Pass 1: Checking inodes, blocks, and sizes +Pass 2: Checking directory structure +Pass 3: Checking directory connectivity +Pass 4: Checking reference counts +Pass 5: Checking group summary information +test_filesys: 11/16 files (0.0% non-contiguous), 21/100 blocks +Exit status is 0 diff --git a/tests/f_invalid_bad_inode/image.gz b/tests/f_invalid_bad_inode/image.gz new file mode 100644 index 0000000000000000000000000000000000000000..5dac14705634bdd79b6561ae1f1a6d53c5defae0 GIT binary patch literal 623 zcmb2|=HMtQX!c`b&dg0rPi1&}*ET~qP=?_{`E(Z5w*k4VYdJI@sVoz9Wf3nenot(t zxN)+)pyTC*XA_oB)7!PHQ?F@t)8q#Wn)KfBHF5RnDMbXfC)J!(ty`koVde7q_rdw! z-@Q{U|Nidp{kxOAIULqYbrh<(DIRlK?NgT%aB9)Tyak&K{yn{OsDi`!;fdW#Zt6v! z+hTuRJX!D9Jqh;90(wV3{d@DF`S5zadwYwjGe7=4a_RWF#}a!Z=5i)pKE3wj)2hEG zryVz!(w;xR=Hr%)Hsy~l{BpY)m$%*8c1z_xxxIFFAGDuW6(4_Vtt|a5evesIZsE7X z+x&YUzs=7*9lme=@%vNOY|xWWp1;st{KQd-o{d{){%@UN=AOPxVBPzR&L94-y3T$7 zUE}=M4*H(6&mZuN>Prptzg%Ql-Bv$YdztvMW$D|(mt|cwzPb6+<`_jwd)rv+>{l)I zaq;f|>QAKpcul@&87nZL zfRg^`&x$<9i*{@>xYw8Ced&+=1A%MDqBxEo{j&Uei|Mu8?5S^mWohxh&yCEzeVcjd z>Rx@hmpA@DJs5NR-{jQa|0iFcrmAOqF-GQpqR#yD#|y9b%|HJCef09`-S-wV_r8{Y zJ}LFOJ+E~1Xa9)Ae=qw3FVy~d+&6bsXnNMtxyesA-hCRo^ssyX6t&e$PjVk!w2u+R UainryxW+Sn|Gs|@!vsbK066d