From 62e3e7fe4f32c2186e848f37b7f977835975413e Mon Sep 17 00:00:00 2001 From: Theodore Ts'o Date: Sun, 7 Oct 2001 02:13:30 -0400 Subject: [PATCH] journal.c (clear_v2_journal_fields, e2fsck_journal_load): If the V2 fields are set on a V1 journal superblock, or an internal V2 journal has s_nr_users is non-zero, clear the entire journal superblock beyond the V1 superblock. This fixes botched V1->V2 updates. problem.c, problem.h (PR_0_CLEAR_V2_JOURNAL): Add new problem code. f_bad_local_jnl: New test which tests for a V2 journal with bad fields caused by a botched V1->V2 upgrade. --- e2fsck/ChangeLog | 10 ++++++++++ e2fsck/journal.c | 26 ++++++++++++++++++++++++++ e2fsck/problem.c | 6 ++++++ e2fsck/problem.h | 3 +++ tests/ChangeLog | 5 +++++ tests/f_bad_local_jnl/expect.1 | 10 ++++++++++ tests/f_bad_local_jnl/expect.2 | 7 +++++++ tests/f_bad_local_jnl/image.gz | Bin 0 -> 10433 bytes tests/f_bad_local_jnl/name | 1 + 9 files changed, 68 insertions(+) create mode 100644 tests/f_bad_local_jnl/expect.1 create mode 100644 tests/f_bad_local_jnl/expect.2 create mode 100644 tests/f_bad_local_jnl/image.gz create mode 100644 tests/f_bad_local_jnl/name diff --git a/e2fsck/ChangeLog b/e2fsck/ChangeLog index ad944da..629b012 100644 --- a/e2fsck/ChangeLog +++ b/e2fsck/ChangeLog @@ -1,3 +1,13 @@ +2001-10-07 Theodore Tso + + * journal.c (clear_v2_journal_fields, e2fsck_journal_load): If the + V2 fields are set on a V1 journal superblock, or an + internal V2 journal has s_nr_users is non-zero, clear the + entire journal superblock beyond the V1 superblock. This + fixes botched V1->V2 updates. + + * problem.c, problem.h (PR_0_CLEAR_V2_JOURNAL): Add new problem code. + 2001-09-20 Theodore Tso * e2fsck.h, journal.c (e2fsck_move_ext3_journal): Add new function diff --git a/e2fsck/journal.c b/e2fsck/journal.c index 0bff025..62d4812 100644 --- a/e2fsck/journal.c +++ b/e2fsck/journal.c @@ -351,6 +351,24 @@ static errcode_t e2fsck_journal_fix_bad_inode(e2fsck_t ctx, return 0; } +#define V1_SB_SIZE 0x0024 +static void clear_v2_journal_fields(journal_t *journal) +{ + e2fsck_t ctx = journal->j_dev; + struct buffer_head *jbh = journal->j_sb_buffer; + struct problem_context pctx; + + clear_problem_context(&pctx); + + if (!fix_problem(ctx, PR_0_CLEAR_V2_JOURNAL, &pctx)) + return; + + memset(((char *) journal->j_superblock) + V1_SB_SIZE, 0, + ctx->fs->blocksize-V1_SB_SIZE); + mark_buffer_dirty(journal->j_sb_buffer, 1); +} + + static errcode_t e2fsck_journal_load(journal_t *journal) { e2fsck_t ctx = journal->j_dev; @@ -375,10 +393,18 @@ static errcode_t e2fsck_journal_load(journal_t *journal) switch (ntohl(jsb->s_header.h_blocktype)) { case JFS_SUPERBLOCK_V1: journal->j_format_version = 1; + if (jsb->s_feature_compat || + jsb->s_feature_incompat || + jsb->s_feature_ro_compat || + jsb->s_nr_users) + clear_v2_journal_fields(journal); break; case JFS_SUPERBLOCK_V2: journal->j_format_version = 2; + if (jsb->s_nr_users && + (ctx->fs->io == ctx->journal_io)) + clear_v2_journal_fields(journal); if (ntohl(jsb->s_nr_users) > 1) { fix_problem(ctx, PR_0_JOURNAL_UNSUPP_MULTIFS, &pctx); return EXT2_ET_JOURNAL_UNSUPP_VERSION; diff --git a/e2fsck/problem.c b/e2fsck/problem.c index 34f4f30..58b8724 100644 --- a/e2fsck/problem.c +++ b/e2fsck/problem.c @@ -287,6 +287,12 @@ static const struct e2fsck_problem problem_table[] = { N_("Error moving @j: %m\n\n"), PROMPT_NONE, 0 }, + /* Clearing V2 journal superblock */ + { PR_0_CLEAR_V2_JOURNAL, + N_("Found invalid V2 @j @S fields (from V1 journal).\n" + "Clearing fields beyond the V1 @j @S...\n\n"), + PROMPT_NONE, 0 }, + /* Pass 1 errors */ /* Pass 1: Checking inodes, blocks, and sizes */ diff --git a/e2fsck/problem.h b/e2fsck/problem.h index e7ddf76..6a234b7 100644 --- a/e2fsck/problem.h +++ b/e2fsck/problem.h @@ -161,6 +161,9 @@ struct problem_context { /* Error moving journal */ #define PR_0_ERR_MOVE_JOURNAL 0x000029 +/* Clearing V2 journal superblock */ +#define PR_0_CLEAR_V2_JOURNAL 0x00002A + /* * Pass 1 errors */ diff --git a/tests/ChangeLog b/tests/ChangeLog index 9b0e810..2fd5c6c 100644 --- a/tests/ChangeLog +++ b/tests/ChangeLog @@ -1,3 +1,8 @@ +2001-10-07 Theodore Tso + + * f_bad_local_jnl: New test which tests for a V2 journal with bad + fields caused by a botched V1->V2 upgrade. + 2001-09-20 Theodore Tso * Release of E2fsprogs 1.25 diff --git a/tests/f_bad_local_jnl/expect.1 b/tests/f_bad_local_jnl/expect.1 new file mode 100644 index 0000000..d8f6551 --- /dev/null +++ b/tests/f_bad_local_jnl/expect.1 @@ -0,0 +1,10 @@ +Found invalid V2 journal superblock fields (from V1 journal). +Clearing fields beyond the V1 journal superblock... + +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/256 files (0.0% non-contiguous), 1080/8192 blocks +Exit status is 0 diff --git a/tests/f_bad_local_jnl/expect.2 b/tests/f_bad_local_jnl/expect.2 new file mode 100644 index 0000000..632dc71 --- /dev/null +++ b/tests/f_bad_local_jnl/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/256 files (0.0% non-contiguous), 1080/8192 blocks +Exit status is 0 diff --git a/tests/f_bad_local_jnl/image.gz b/tests/f_bad_local_jnl/image.gz new file mode 100644 index 0000000000000000000000000000000000000000..addd58aa40257f4dc36a21bd4440f49b93e4c535 GIT binary patch literal 10433 zcmeIyeNYo;9tUtNH(F04r_Q0Gk#jt?R|jZoBWD;u+Yzmlmk>x`Aqj|rZi@J}Akh$& z3a4D8*7K!N1VkapW_J}_I2IFBuD(=Ws%~~Q5b$LL-4(^c5{ZUfdw+HA5C7@h&0KGv zzn*!Xd7gQm&+j+iz|wc$t?9Ccz2mzvCnI~k&od`f`rT=Z7Bna@y%>?=Pt8c2(a`YRZ4E63Yv$eHUGCMnZRvw2eOB zWeaOw5|*9r^NI{eJS>=el5~YF3YfWrt(NLU_f~1QZ#`LyR_M~xnLSCWz~O#rreCw| z3aqoj8BwSe+#ncx@+R6f=VF`YSg`fhq0l*X9x}UP@OBH+Is5Yb$zFI~VEfa}zO8*; zB(ihy;M2he-bp((f4Hy8#r#UV`F8_%>x#?zcim-QmA#g4T8;&~`zkX+mXE!3wJh6k zz1Qmh&3DRn-NWgFJ*~mlUNz5p^Ge?&8S86@@2L+O>if)1>QjcsJ~)It7noM*Z`lVv zSV6hGJv!nzr*nA6`+Ytb+IWJfF>O>623wYKmb%8!lr?%&A!y4=8Rzr1F_t4hCF92n zPK{#MiY9b+A2}3OSa5xHQDb*ji7@-__7mj|J$Hf2I>RAv##ry1AC8Sqh*(ezyz_x~ z_vnPS$n>#sLw?6~m)`jH1^#PkOxXQr@2*8-t|=c3KWbeO$W07!ZX5iFRS?5bt9mwH zACXpQuSCD-&^pJ|(O7Iq7@y8Z`HvscdG=%yH|3Ygz3O`ow1J29LN7P3E zTn5|KdZ3;%()a+Ikg&9M0ToTOBGDV~!f z@1m#RnFEQv#$2icj~)Pe%}&tes2;Ic!55C&5yZoE;W}ab1ZoAeS(s2lWk5TGl2w!h z+Afq{qqac1%Hvxj(zhgNYhzI<)67}Lcr1K}{j0dX!(7jv6gPIjL+oDST(G&6{n}mV zsSHMLGCvTfQ47p4L=B1rQe_N5*b37^Nj)TWrZtiXlX3Z~I0pRGp5yO%e^%Q6zv=EcVBPnZE}br#Fy4Rm+MxS) zvTpV1&I1>Z8W*Td0AWkMN!D>^0rV*Ld+=MpBtw%xJAlYA5!epE6bgY(_g3v$8^GG# z_==q5+4igWXF0$Ldmp}1i`bN@lnjS*q+L`Vt{sREqhdL|J8K}VnM66nf#hM~V5b8f zLA7A71G6b!)8n9YVd4aO9<)IyE1{=C>x4669j5fvn50@b*$+N6oQaSh zrq+oHVk8yVpVVfPGs`mqRN6ly1QvCCvRF(NLI0{tBEJwh{z*!k$2RWdcvf$tVP)i{pw48x) zC8C;5{ut0XY5%!+UPOJym5ZBVO)n@HLyD1DYzfmQhC9%0Ot%>8z$P(Q2xBlB&AjG{ zhzr5+P4)m$hniv5Kr|F4N19p2?cU;y52a$DZO(*7DhJx>l;l$iDBme{QCdhB9`8qe z%54r$D5EmD9pREVDvqh;5uP(h+#> zfV>y=u)D?QrkIP^uf!Loz^&|G#B~SF)$DO`!$J5F`=$7Ntoa3b16rePw8?9!jgY2X zl1-&RdF9f6ssJif#Lu8sLR%CGy;vZ57D`bl<>V14Nui)goNIMU6mps_V~dINo6INJ zqXfPQ?qUxT_0P@C>?xx0IsBU4qd7O%T*4mGT$l@AWA|(73KJrcS|*#@9xm;qwsAx5 zmEo!ovXo2k)G1Mw9b-eeHC6z#vs{;3;j#4?Ls>-A++&I)n>nRb6-WlMaa@LAvT)|i z#3J=-0rG%ZBHE>opHHn8ZPh1KQyWAYy(E)L7Uk)skEk7@!kG99WTN`C;qMDgo%S=L zlo+Ly>{owhFxQ|PL5BgY!DfM14W=wK1*8l}7PbuRFu;9iL9ye`Tg%FC@&dd7FTe}% z0=xh(zzgsKyZ|r23-AKG058A`@B+L5FTe}%0=xh(zzgsKzf|BAHgf-~pDtPcy_e34 X{H53N=l|yfHjj(AxZUpKv)kvN^|vWX literal 0 HcmV?d00001 diff --git a/tests/f_bad_local_jnl/name b/tests/f_bad_local_jnl/name new file mode 100644 index 0000000..8b77264 --- /dev/null +++ b/tests/f_bad_local_jnl/name @@ -0,0 +1 @@ +test for corrupt local journal (bad V1->V2 journal upgrade) -- 1.8.3.1