summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--e2fsck/ChangeLog9
-rw-r--r--e2fsck/e2fsck.h2
-rw-r--r--e2fsck/pass1.c36
-rw-r--r--e2fsck/pass2.c8
4 files changed, 52 insertions, 3 deletions
diff --git a/e2fsck/ChangeLog b/e2fsck/ChangeLog
index b6fcd66d..ec3980c0 100644
--- a/e2fsck/ChangeLog
+++ b/e2fsck/ChangeLog
@@ -1,3 +1,12 @@
+2007-04-06 Theodore Tso <tytso@mit.edu>
+
+ * e2fsck.h, pass1.c, pass2.c: If e2fsck.conf configures a
+ scratch_files directory which is available, and the number
+ of directories exceeds scratch_files.numdirs_threshold,
+ then try to use the tdb library to store the inode count
+ abstraction. This allows us to check very large
+ filesystems without needing as much physical memory.
+
2007-04-04 Theodore Tso <tytso@mit.edu>
* dirinfo.c, pass2.c, pass3.c, rehash.c, e2fsck.h: Change the
diff --git a/e2fsck/e2fsck.h b/e2fsck/e2fsck.h
index a7eba37e..ae337907 100644
--- a/e2fsck/e2fsck.h
+++ b/e2fsck/e2fsck.h
@@ -420,6 +420,8 @@ extern void e2fsck_move_ext3_journal(e2fsck_t ctx);
extern int e2fsck_fix_ext3_journal_hint(e2fsck_t ctx);
/* pass1.c */
+extern void e2fsck_setup_tdb_icount(e2fsck_t ctx, int flags,
+ ext2_icount_t *ret);
extern void e2fsck_use_inode_shortcuts(e2fsck_t ctx, int bool);
extern int e2fsck_pass1_check_device_inode(ext2_filsys fs,
struct ext2_inode *inode);
diff --git a/e2fsck/pass1.c b/e2fsck/pass1.c
index d45c4987..4a888118 100644
--- a/e2fsck/pass1.c
+++ b/e2fsck/pass1.c
@@ -440,6 +440,36 @@ static void check_is_really_dir(e2fsck_t ctx, struct problem_context *pctx,
}
}
+extern void e2fsck_setup_tdb_icount(e2fsck_t ctx, int flags,
+ ext2_icount_t *ret)
+{
+ ext2_ino_t num_dirs;
+ errcode_t retval;
+ char *tdb_dir, uuid[40];
+ int fd, threshold, enable;
+
+ *ret = 0;
+
+ profile_get_string(ctx->profile, "scratch_files", "directory", 0, 0,
+ &tdb_dir);
+ profile_get_integer(ctx->profile, "scratch_files",
+ "numdirs_threshold", 0, 0, &threshold);
+ profile_get_boolean(ctx->profile, "scratch_files",
+ "icount", 0, 1, &enable);
+
+ retval = ext2fs_get_num_dirs(ctx->fs, &num_dirs);
+ if (retval)
+ num_dirs = 1024; /* Guess */
+
+ if (!enable || !tdb_dir || access(tdb_dir, W_OK) ||
+ (threshold && num_dirs <= threshold))
+ return;
+
+ retval = ext2fs_create_icount_tdb(ctx->fs, tdb_dir, flags, ret);
+ if (retval)
+ *ret = 0;
+}
+
void e2fsck_pass1(e2fsck_t ctx)
{
int i;
@@ -526,8 +556,10 @@ void e2fsck_pass1(e2fsck_t ctx)
ctx->flags |= E2F_FLAG_ABORT;
return;
}
- pctx.errcode = ext2fs_create_icount2(fs, 0, 0, 0,
- &ctx->inode_link_info);
+ e2fsck_setup_tdb_icount(ctx, 0, &ctx->inode_link_info);
+ if (!ctx->inode_link_info)
+ pctx.errcode = ext2fs_create_icount2(fs, 0, 0, 0,
+ &ctx->inode_link_info);
if (pctx.errcode) {
fix_problem(ctx, PR_1_ALLOCATE_ICOUNT, &pctx);
ctx->flags |= E2F_FLAG_ABORT;
diff --git a/e2fsck/pass2.c b/e2fsck/pass2.c
index e4479308..715919d6 100644
--- a/e2fsck/pass2.c
+++ b/e2fsck/pass2.c
@@ -114,7 +114,13 @@ void e2fsck_pass2(e2fsck_t ctx)
if (!(ctx->options & E2F_OPT_PREEN))
fix_problem(ctx, PR_2_PASS_HEADER, &cd.pctx);
- cd.pctx.errcode = ext2fs_create_icount2(fs, EXT2_ICOUNT_OPT_INCREMENT,
+ e2fsck_setup_tdb_icount(ctx, EXT2_ICOUNT_OPT_INCREMENT,
+ &ctx->inode_count);
+ if (ctx->inode_count)
+ cd.pctx.errcode = 0;
+ else
+ cd.pctx.errcode = ext2fs_create_icount2(fs,
+ EXT2_ICOUNT_OPT_INCREMENT,
0, ctx->inode_link_info,
&ctx->inode_count);
if (cd.pctx.errcode) {