From e72a9ba39471364ad2f9397f645ca547090e3485 Mon Sep 17 00:00:00 2001 From: Theodore Ts'o Date: Fri, 25 Jun 1999 15:40:18 +0000 Subject: [PATCH] ChangeLog, e2fsck.h, pass1.c, pass2.c, pass4.c, swapfs.c: e2fsck.h: pass1.c (pass1_get_blocks, pass1_read_inode, pass1_write_inode, pass1_check_directory, e2fsck_use_inode_shortcuts): Make pass1_* be private static functions, and create new function e2fsck_use_inode_shortcuts which sets and clears the inode shortcut functions in the fs structure. e2fsck.h: pass2.c (e2fsck_process_bad_inode): Make process_bad_inode() an exported function. pass4.c (e2fsck_pass4): Call e2fsck_process_bad_inode to check if a disconnected inode has any problems before connecting it to /lost+found. Bug and suggested fix by Pavel Machek ChangeLog, swapfs.c: swapfs.c (ext2fs_swap_inode): Add compatibility for Linux 2.3 kernels that use i_generation instead of i_version. Patch supplied by Jon Bright . ChangeLog, mke2fs.8.in: mke2fs.8.in: Fix typo in man page which caused the badblocks command to not show up in the "SEE ALSO" section. ChangeLog, expect.1, expect.2, image.gz, name: f_recnect_bad: New test which checks the case where a disconnect inode also bad inode fields; we need to make sure e2fsck offers to fix the inode (or clear the inode, as necessary). --- e2fsck/ChangeLog | 20 +++++++++++++++++++- e2fsck/e2fsck.h | 23 ++++++++++------------- e2fsck/pass1.c | 41 ++++++++++++++++++++++++++++------------- e2fsck/pass2.c | 6 +++--- e2fsck/pass4.c | 2 ++ e2fsck/swapfs.c | 6 ++---- lib/ext2fs/ChangeLog | 8 +++++++- lib/ext2fs/swapfs.c | 4 ++++ misc/ChangeLog | 5 +++++ misc/mke2fs.8.in | 2 +- tests/ChangeLog | 6 ++++++ tests/f_recnect_bad/expect.1 | 29 +++++++++++++++++++++++++++++ tests/f_recnect_bad/expect.2 | 7 +++++++ tests/f_recnect_bad/image.gz | Bin 0 -> 543 bytes tests/f_recnect_bad/name | 1 + 15 files changed, 124 insertions(+), 36 deletions(-) create mode 100644 tests/f_recnect_bad/expect.1 create mode 100644 tests/f_recnect_bad/expect.2 create mode 100644 tests/f_recnect_bad/image.gz create mode 100644 tests/f_recnect_bad/name diff --git a/e2fsck/ChangeLog b/e2fsck/ChangeLog index 5894054..82f8c34 100644 --- a/e2fsck/ChangeLog +++ b/e2fsck/ChangeLog @@ -1,4 +1,22 @@ -1999-06-21 +1999-06-25 + + * e2fsck.h: + * pass1.c (pass1_get_blocks, pass1_read_inode, pass1_write_inode, + pass1_check_directory, e2fsck_use_inode_shortcuts): Make + pass1_* be private static functions, and create new + function e2fsck_use_inode_shortcuts which sets and clears + the inode shortcut functions in the fs structure. + + * e2fsck.h: + * pass2.c (e2fsck_process_bad_inode): Make process_bad_inode() an + exported function. + + * pass4.c (e2fsck_pass4): Call e2fsck_process_bad_inode to check + if a disconnected inode has any problems before + connecting it to /lost+found. Bug and suggested fix by + Pavel Machek + +1999-06-21 * unix.c (main): Add missing space in the disk write-protected message. diff --git a/e2fsck/e2fsck.h b/e2fsck/e2fsck.h index 12c5971..782edbc 100644 --- a/e2fsck/e2fsck.h +++ b/e2fsck/e2fsck.h @@ -241,15 +241,6 @@ extern void e2fsck_free_context(e2fsck_t ctx); extern int e2fsck_run(e2fsck_t ctx); -/* pass1.c */ -extern errcode_t pass1_check_directory(ext2_filsys fs, ino_t ino); -extern errcode_t pass1_get_blocks(ext2_filsys fs, ino_t ino, blk_t *blocks); -extern errcode_t pass1_read_inode(ext2_filsys fs, ino_t ino, - struct ext2_inode *inode); -extern errcode_t pass1_write_inode(ext2_filsys fs, ino_t ino, - struct ext2_inode *inode); -extern int e2fsck_pass1_check_device_inode(struct ext2_inode *inode); - /* badblock.c */ extern void read_bad_blocks_file(e2fsck_t ctx, const char *bad_blocks_file, int replace_bad_blocks); @@ -267,6 +258,16 @@ extern struct dir_info *e2fsck_dir_info_iter(e2fsck_t ctx, int *control); extern const char *ehandler_operation(const char *op); extern void ehandler_init(io_channel channel); +/* pass1.c */ +extern void e2fsck_use_inode_shortcuts(e2fsck_t ctx, int bool); +extern int e2fsck_pass1_check_device_inode(struct ext2_inode *inode); + +/* pass2.c */ +extern int e2fsck_process_bad_inode(e2fsck_t ctx, ino_t dir, ino_t ino); + +/* pass3.c */ +extern int e2fsck_reconnect_file(e2fsck_t ctx, ino_t inode); + /* super.c */ void check_super_block(e2fsck_t ctx); errcode_t e2fsck_get_device_size(e2fsck_t ctx); @@ -298,7 +299,3 @@ extern void mtrace_print(char *mesg); #endif extern blk_t get_backup_sb(ext2_filsys fs); -/* - * pass3.c - */ -extern int e2fsck_reconnect_file(e2fsck_t ctx, ino_t inode); diff --git a/e2fsck/pass1.c b/e2fsck/pass1.c index 6766f41..5ebd6e0 100644 --- a/e2fsck/pass1.c +++ b/e2fsck/pass1.c @@ -239,10 +239,7 @@ void e2fsck_pass1(e2fsck_t ctx) mark_table_blocks(ctx); block_buf = (char *) e2fsck_allocate_memory(ctx, fs->blocksize * 3, "block interate buffer"); - fs->get_blocks = pass1_get_blocks; - fs->check_directory = pass1_check_directory; - fs->read_inode = pass1_read_inode; - fs->write_inode = pass1_write_inode; + e2fsck_use_inode_shortcuts(ctx, 1); ehandler_operation("doing inode scan"); pctx.errcode = ext2fs_open_inode_scan(fs, ctx->inode_buffer_blocks, &scan); @@ -501,10 +498,7 @@ void e2fsck_pass1(e2fsck_t ctx) } ext2fs_free_mem((void **) &inodes_to_process); endit: - fs->get_blocks = 0; - fs->check_directory = 0; - fs->read_inode = 0; - fs->write_inode = 0; + e2fsck_use_inode_shortcuts(ctx, 0); ext2fs_free_mem((void **) &block_buf); ext2fs_free_block_bitmap(ctx->block_illegal_map); @@ -1313,12 +1307,12 @@ static void mark_table_blocks(e2fsck_t ctx) } /* - * This subroutines short circuits ext2fs_get_blocks and + * Thes subroutines short circuits ext2fs_get_blocks and * ext2fs_check_directory; we use them since we already have the inode * structure, so there's no point in letting the ext2fs library read * the inode again. */ -errcode_t pass1_get_blocks(ext2_filsys fs, ino_t ino, blk_t *blocks) +static errcode_t pass1_get_blocks(ext2_filsys fs, ino_t ino, blk_t *blocks) { e2fsck_t ctx = (e2fsck_t) fs->priv_data; int i; @@ -1331,7 +1325,8 @@ errcode_t pass1_get_blocks(ext2_filsys fs, ino_t ino, blk_t *blocks) return 0; } -errcode_t pass1_read_inode(ext2_filsys fs, ino_t ino, struct ext2_inode *inode) +static errcode_t pass1_read_inode(ext2_filsys fs, ino_t ino, + struct ext2_inode *inode) { e2fsck_t ctx = (e2fsck_t) fs->priv_data; @@ -1341,7 +1336,7 @@ errcode_t pass1_read_inode(ext2_filsys fs, ino_t ino, struct ext2_inode *inode) return 0; } -errcode_t pass1_write_inode(ext2_filsys fs, ino_t ino, +static errcode_t pass1_write_inode(ext2_filsys fs, ino_t ino, struct ext2_inode *inode) { e2fsck_t ctx = (e2fsck_t) fs->priv_data; @@ -1351,7 +1346,7 @@ errcode_t pass1_write_inode(ext2_filsys fs, ino_t ino, return EXT2_ET_CALLBACK_NOTHANDLED; } -errcode_t pass1_check_directory(ext2_filsys fs, ino_t ino) +static errcode_t pass1_check_directory(ext2_filsys fs, ino_t ino) { e2fsck_t ctx = (e2fsck_t) fs->priv_data; @@ -1362,3 +1357,23 @@ errcode_t pass1_check_directory(ext2_filsys fs, ino_t ino) return EXT2_ET_NO_DIRECTORY; return 0; } + +void e2fsck_use_inode_shortcuts(e2fsck_t ctx, int bool) +{ + ext2_filsys fs = ctx->fs; + + if (bool) { + fs->get_blocks = pass1_get_blocks; + fs->check_directory = pass1_check_directory; + fs->read_inode = pass1_read_inode; + fs->write_inode = pass1_write_inode; + ctx->stashed_ino = 0; + } else { + fs->get_blocks = 0; + fs->check_directory = 0; + fs->read_inode = 0; + fs->write_inode = 0; + } +} + + diff --git a/e2fsck/pass2.c b/e2fsck/pass2.c index 5453c61..38c1eda 100644 --- a/e2fsck/pass2.c +++ b/e2fsck/pass2.c @@ -48,7 +48,6 @@ */ static void deallocate_inode(e2fsck_t ctx, ino_t ino, char* block_buf); -static int process_bad_inode(e2fsck_t ctx, ino_t dir, ino_t ino); static int check_dir_block(ext2_filsys fs, struct ext2_db_entry *dir_blocks_info, void *priv_data); @@ -451,7 +450,8 @@ static int check_dir_block(ext2_filsys fs, if (ctx->inode_bad_map && ext2fs_test_inode_bitmap(ctx->inode_bad_map, dirent->inode)) { - if (process_bad_inode(ctx, ino, dirent->inode)) { + if (e2fsck_process_bad_inode(ctx, ino, + dirent->inode)) { dirent->inode = 0; dir_modified++; goto next; @@ -585,7 +585,7 @@ static void deallocate_inode(e2fsck_t ctx, ino_t ino, } } -static int process_bad_inode(e2fsck_t ctx, ino_t dir, ino_t ino) +extern int e2fsck_process_bad_inode(e2fsck_t ctx, ino_t dir, ino_t ino) { ext2_filsys fs = ctx->fs; struct ext2_inode inode; diff --git a/e2fsck/pass4.c b/e2fsck/pass4.c index adde764..e059cc3 100644 --- a/e2fsck/pass4.c +++ b/e2fsck/pass4.c @@ -123,6 +123,8 @@ void e2fsck_pass4(e2fsck_t ctx) ext2fs_icount_fetch(ctx->inode_link_info, i, &link_count); ext2fs_icount_fetch(ctx->inode_count, i, &link_counted); if (link_counted == 0) { + if (e2fsck_process_bad_inode(ctx, 0, i)) + continue; if (disconnect_inode(ctx, i)) continue; ext2fs_icount_fetch(ctx->inode_link_info, i, diff --git a/e2fsck/swapfs.c b/e2fsck/swapfs.c index 605b8e3..3a8a878 100644 --- a/e2fsck/swapfs.c +++ b/e2fsck/swapfs.c @@ -114,8 +114,7 @@ static void swap_inodes(e2fsck_t ctx) errcode_t retval; struct ext2_inode * inode; - fs->read_inode = pass1_read_inode; - fs->get_blocks = pass1_get_blocks; + e2fsck_use_inode_shortcuts(ctx, 1); retval = ext2fs_get_mem(fs->blocksize * fs->inode_blocks_per_group, (void **) &buf); @@ -179,8 +178,7 @@ static void swap_inodes(e2fsck_t ctx) } ext2fs_free_mem((void **) &buf); ext2fs_free_mem((void **) &block_buf); - fs->read_inode = 0; - fs->get_blocks = 0; + e2fsck_use_inode_shortcuts(ctx, 0); } void swap_filesys(e2fsck_t ctx) diff --git a/lib/ext2fs/ChangeLog b/lib/ext2fs/ChangeLog index 9fc24e9..a051d4f 100644 --- a/lib/ext2fs/ChangeLog +++ b/lib/ext2fs/ChangeLog @@ -1,4 +1,10 @@ -1999-06-21 +1999-06-23 + + * swapfs.c (ext2fs_swap_inode): Add compatibility for Linux 2.3 + kernels that use i_generation instead of i_version. Patch + supplied by Jon Bright . + +1999-06-21 * dir_iterate.c (ext2fs_process_dir_block): Check for corrupted directory entry before calling the callback function. diff --git a/lib/ext2fs/swapfs.c b/lib/ext2fs/swapfs.c index 63c5c2b..66540b3 100644 --- a/lib/ext2fs/swapfs.c +++ b/lib/ext2fs/swapfs.c @@ -100,7 +100,11 @@ void ext2fs_swap_inode(ext2_filsys fs, struct ext2_inode *t, for (i = 0; i < EXT2_N_BLOCKS; i++) t->i_block[i] = f->i_block[i]; } +#if defined(HAVE_EXT2_INODE_VERSION) t->i_version = ext2fs_swab32(f->i_version); +#else + t->i_generation = ext2fs_swab32(f->i_generation); +#endif t->i_file_acl = ext2fs_swab32(f->i_file_acl); t->i_dir_acl = ext2fs_swab32(f->i_dir_acl); t->i_faddr = ext2fs_swab32(f->i_faddr); diff --git a/misc/ChangeLog b/misc/ChangeLog index 014db64..6a94aeb 100644 --- a/misc/ChangeLog +++ b/misc/ChangeLog @@ -1,3 +1,8 @@ +1999-06-24 + + * mke2fs.8.in: Fix typo in man page which caused the badblocks + command to not show up in the "SEE ALSO" section. + 1999-05-02 * findsuper.c: Added documentation from aeb@cwi.nl; some minor diff --git a/misc/mke2fs.8.in b/misc/mke2fs.8.in index df8cc99..94cb969 100644 --- a/misc/mke2fs.8.in +++ b/misc/mke2fs.8.in @@ -208,7 +208,7 @@ There may be some other ones. Please, report them to the author. is part of the e2fsprogs package and is available for anonymous ftp from tsx-11.mit.edu in /pub/linux/packages/ext2fs. .SH SEE ALSO -.BT badblocks (8), +.BR badblocks (8), .BR dumpe2fs (8), .BR e2fsck (8), .BR tune2fs (8) diff --git a/tests/ChangeLog b/tests/ChangeLog index 6680109..5e00535 100644 --- a/tests/ChangeLog +++ b/tests/ChangeLog @@ -1,3 +1,9 @@ +1999-06-25 + + * f_recnect_bad: New test which checks the case where a disconnect + inode also bad inode fields; we need to make sure e2fsck + offers to fix the inode (or clear the inode, as necessary). + 1999-03-14 Theodore Ts'o * f_lpffile: New test which checks how e2fsck handles a the case diff --git a/tests/f_recnect_bad/expect.1 b/tests/f_recnect_bad/expect.1 new file mode 100644 index 0000000..96fe9db --- /dev/null +++ b/tests/f_recnect_bad/expect.1 @@ -0,0 +1,29 @@ +Pass 1: Checking inodes, blocks, and sizes +Pass 2: Checking directory structure +i_faddr for inode 15 (/test/quux) is 23, should be zero. +Clear? yes + +i_dir_acl for inode 15 (/test/quux) is 12, should be zero. +Clear? yes + +i_faddr for inode 13 (/test/???) is 12, should be zero. +Clear? yes + +i_file_acl for inode 13 (/test/???) is 12, should be zero. +Clear? yes + +Pass 3: Checking directory connectivity +Unconnected directory inode 13 (/test/???) +Connect to /lost+found? yes + +Pass 4: Checking reference counts +Inode 13 ref count is 4, should be 3. Fix? yes + +Inode 28 (...) has a bad mode (0177777). +Clear? yes + +Pass 5: Checking group summary information + +test_filesys: ***** FILE SYSTEM WAS MODIFIED ***** +test_filesys: 15/32 files (0.0% non-contiguous), 26/100 blocks +Exit status is 1 diff --git a/tests/f_recnect_bad/expect.2 b/tests/f_recnect_bad/expect.2 new file mode 100644 index 0000000..fc68e79 --- /dev/null +++ b/tests/f_recnect_bad/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: 15/32 files (0.0% non-contiguous), 26/100 blocks +Exit status is 0 diff --git a/tests/f_recnect_bad/image.gz b/tests/f_recnect_bad/image.gz new file mode 100644 index 0000000000000000000000000000000000000000..37dcdf9b2e2dab049abbcaab7133356964abeb7b GIT binary patch literal 543 zcmb2|=HOsxC^lze&dg0rPi1&}+dexuQH1@0dA-P%%q)|v-KE7nv9`a zC2w}ebi8r1ni%!7>FmqXM^+y!^SWE|-#fSH?zPiD{@?qk|JugJ^3^@7w|nY;|2ez) zy1e|J%auRAOHF*1^UwO_qG=APJ;xv4eEaXU#EL1+C#4ud0_xtMuRH$y=j`A8k9W6Q z-{hZA^!M=Gv{mBkcBian)2aE}X}|sX+WN0s;&!|%N>RPkwZ`q%#H}Z$zE58ku6#YH z%xKo7ulLu=zrKI$V1o7eFO%i3@0U*h`FC-h{;Ovv{oA^}=Ko8a8}@Q*%zwWtXD5H( zA5s6eXaE1_D`uz1{q1GFlBK(#pF!vJ&)4VeR_gwmQ@-Z*l&k8$Cq=zFd+&Pidh@%l z%aX7E-eE71_x8KH|F>nor}OuwN!dy9l=7Y1KlRd|`6kOg^M|+ub07G_{7l~9f5T7q zGxiDp7(esRs0RyK@JD6-`)q%6^V|7SXTOw~R4w%0Fei-r^L?!|_0>lId$-(wpDm=b mvMll6=B)=l*9XXEFa5p$Cp!bRz>od4%zvNmJ