*/
#define _GNU_SOURCE 1 /* get strnlen() */
+#include "config.h"
#include <string.h>
#include "e2fsck.h"
*/
static void deallocate_inode(e2fsck_t ctx, ext2_ino_t ino, char* block_buf);
static int check_dir_block(ext2_filsys fs,
- struct ext2_db_entry *dir_blocks_info,
+ struct ext2_db_entry2 *dir_blocks_info,
void *priv_data);
static int allocate_dir_block(e2fsck_t ctx,
- struct ext2_db_entry *dir_blocks_info,
+ struct ext2_db_entry2 *dir_blocks_info,
char *buf, struct problem_context *pctx);
static void clear_htree(e2fsck_t ctx, ext2_ino_t ino);
static int htree_depth(struct dx_dir_info *dx_dir,
struct check_dir_struct cd;
struct dx_dir_info *dx_dir;
struct dx_dirblock_info *dx_db, *dx_parent;
+ unsigned int save_type;
int b;
int i, depth;
problem_t code;
&ctx->inode_count);
if (ctx->inode_count)
cd.pctx.errcode = 0;
- else
+ else {
+ e2fsck_set_bitmap_type(fs, EXT2FS_BMAP64_RBTREE,
+ "inode_count", &save_type);
cd.pctx.errcode = ext2fs_create_icount2(fs,
EXT2_ICOUNT_OPT_INCREMENT,
0, ctx->inode_link_info,
&ctx->inode_count);
+ fs->default_bitmap_type = save_type;
+ }
if (cd.pctx.errcode) {
fix_problem(ctx, PR_2_ALLOCATE_ICOUNT, &cd.pctx);
ctx->flags |= E2F_FLAG_ABORT;
cd.buf = buf;
cd.ctx = ctx;
cd.count = 1;
- cd.max = ext2fs_dblist_count(fs->dblist);
+ cd.max = ext2fs_dblist_count2(fs->dblist);
if (ctx->progress)
(void) (ctx->progress)(ctx, 2, 0, cd.max);
if (fs->super->s_feature_compat & EXT2_FEATURE_COMPAT_DIR_INDEX)
- ext2fs_dblist_sort(fs->dblist, special_dir_block_cmp);
+ ext2fs_dblist_sort2(fs->dblist, special_dir_block_cmp);
- cd.pctx.errcode = ext2fs_dblist_iterate(fs->dblist, check_dir_block,
- &cd);
+ cd.pctx.errcode = ext2fs_dblist_iterate2(fs->dblist, check_dir_block,
+ &cd);
if (ctx->flags & E2F_FLAG_SIGNAL_MASK || ctx->flags & E2F_FLAG_RESTART)
return;
*/
static EXT2_QSORT_TYPE special_dir_block_cmp(const void *a, const void *b)
{
- const struct ext2_db_entry *db_a =
- (const struct ext2_db_entry *) a;
- const struct ext2_db_entry *db_b =
- (const struct ext2_db_entry *) b;
+ const struct ext2_db_entry2 *db_a =
+ (const struct ext2_db_entry2 *) a;
+ const struct ext2_db_entry2 *db_b =
+ (const struct ext2_db_entry2 *) b;
if (db_a->blockcnt && !db_b->blockcnt)
return 1;
struct ext2_dir_entry *dirent,
ext2_ino_t ino, struct problem_context *pctx)
{
- int rec_len, problem = 0;
+ int problem = 0;
+ unsigned int rec_len;
if (!dirent->inode)
problem = PR_2_MISSING_DOT_DOT;
#ifdef ENABLE_HTREE
static void parse_int_node(ext2_filsys fs,
- struct ext2_db_entry *db,
+ struct ext2_db_entry2 *db,
struct check_dir_struct *cd,
struct dx_dir_info *dx_dir,
char *block_buf)
}
static int check_dir_block(ext2_filsys fs,
- struct ext2_db_entry *db,
+ struct ext2_db_entry2 *db,
void *priv_data)
{
struct dx_dir_info *dx_dir;
struct ext2_dir_entry *dirent, *prev;
ext2_dirhash_t hash;
unsigned int offset = 0;
- const char * old_op;
int dir_modified = 0;
int dot_state;
unsigned int rec_len;
- blk_t block_nr = db->blk;
+ blk64_t block_nr = db->blk;
ext2_ino_t ino = db->ino;
ext2_ino_t subdir_parent;
__u16 links;
db->blockcnt, ino);
#endif
- old_op = ehandler_operation(_("reading directory block"));
- cd->pctx.errcode = ext2fs_read_dir_block(fs, block_nr, buf);
+ ehandler_operation(_("reading directory block"));
+ cd->pctx.errcode = ext2fs_read_dir_block3(fs, block_nr, buf, 0);
ehandler_operation(0);
if (cd->pctx.errcode == EXT2_ET_DIR_CORRUPTED)
cd->pctx.errcode = 0; /* We'll handle this ourselves */
} else
goto abort_free_dict;
}
- if ((dirent->name_len & 0xFF) > EXT2_NAME_LEN) {
- if (fix_problem(ctx, PR_2_FILENAME_LONG, &cd->pctx)) {
- dirent->name_len = EXT2_NAME_LEN;
- dir_modified++;
- }
- }
if (dot_state == 0) {
if (check_dot(ctx, dirent, ino, &cd->pctx))
return DIRENT_ABORT;
}
+struct del_block {
+ e2fsck_t ctx;
+ e2_blkcnt_t num;
+};
+
/*
* This function is called to deallocate a block, and is an interator
* functioned called by deallocate inode via ext2fs_iterate_block().
*/
static int deallocate_inode_block(ext2_filsys fs,
- blk_t *block_nr,
+ blk64_t *block_nr,
e2_blkcnt_t blockcnt EXT2FS_ATTR((unused)),
- blk_t ref_block EXT2FS_ATTR((unused)),
+ blk64_t ref_block EXT2FS_ATTR((unused)),
int ref_offset EXT2FS_ATTR((unused)),
void *priv_data)
{
- e2fsck_t ctx = (e2fsck_t) priv_data;
+ struct del_block *p = priv_data;
if (HOLE_BLKADDR(*block_nr))
return 0;
if ((*block_nr < fs->super->s_first_data_block) ||
(*block_nr >= ext2fs_blocks_count(fs->super)))
return 0;
- ext2fs_unmark_block_bitmap2(ctx->block_found_map, *block_nr);
+ ext2fs_unmark_block_bitmap2(p->ctx->block_found_map, *block_nr);
ext2fs_block_alloc_stats2(fs, *block_nr, -1);
+ p->num++;
return 0;
}
struct ext2_inode inode;
struct problem_context pctx;
__u32 count;
+ struct del_block del_block;
e2fsck_read_inode(ctx, ino, &inode, "deallocate_inode");
e2fsck_clear_inode(ctx, ino, &inode, 0, "deallocate_inode");
e2fsck_read_bitmaps(ctx);
ext2fs_inode_alloc_stats2(fs, ino, -1, LINUX_S_ISDIR(inode.i_mode));
- if (ext2fs_file_acl_block(&inode) &&
+ if (ext2fs_file_acl_block(fs, &inode) &&
(fs->super->s_feature_compat & EXT2_FEATURE_COMPAT_EXT_ATTR)) {
- pctx.errcode = ext2fs_adjust_ea_refcount(fs, ext2fs_file_acl_block(&inode),
- block_buf, -1, &count);
+ pctx.errcode = ext2fs_adjust_ea_refcount2(fs,
+ ext2fs_file_acl_block(fs, &inode),
+ block_buf, -1, &count);
if (pctx.errcode == EXT2_ET_BAD_EA_BLOCK_NUM) {
pctx.errcode = 0;
count = 1;
}
if (pctx.errcode) {
- pctx.blk = ext2fs_file_acl_block(&inode);
+ pctx.blk = ext2fs_file_acl_block(fs, &inode);
fix_problem(ctx, PR_2_ADJ_EA_REFCOUNT, &pctx);
ctx->flags |= E2F_FLAG_ABORT;
return;
}
if (count == 0) {
ext2fs_unmark_block_bitmap2(ctx->block_found_map,
- ext2fs_file_acl_block(&inode));
+ ext2fs_file_acl_block(fs, &inode));
ext2fs_block_alloc_stats2(fs,
- ext2fs_file_acl_block(&inode),
- -1);
+ ext2fs_file_acl_block(fs, &inode), -1);
}
- ext2fs_file_acl_block_set(&inode, 0);
+ ext2fs_file_acl_block_set(fs, &inode, 0);
}
- if (!ext2fs_inode_has_valid_blocks(&inode))
+ if (!ext2fs_inode_has_valid_blocks2(fs, &inode))
return;
- if (LINUX_S_ISREG(inode.i_mode) &&
- (inode.i_size_high || inode.i_size & 0x80000000UL))
+ if (LINUX_S_ISREG(inode.i_mode) && EXT2_I_SIZE(&inode) >= 0x80000000UL)
ctx->large_files--;
- pctx.errcode = ext2fs_block_iterate2(fs, ino, 0, block_buf,
- deallocate_inode_block, ctx);
+ del_block.ctx = ctx;
+ del_block.num = 0;
+ pctx.errcode = ext2fs_block_iterate3(fs, ino, 0, block_buf,
+ deallocate_inode_block,
+ &del_block);
if (pctx.errcode) {
fix_problem(ctx, PR_2_DEALLOC_INODE, &pctx);
ctx->flags |= E2F_FLAG_ABORT;
pctx.dir = dir;
pctx.inode = &inode;
- if (ext2fs_file_acl_block(&inode) &&
+ if (ext2fs_file_acl_block(fs, &inode) &&
!(fs->super->s_feature_compat & EXT2_FEATURE_COMPAT_EXT_ATTR)) {
if (fix_problem(ctx, PR_2_FILE_ACL_ZERO, &pctx)) {
- ext2fs_file_acl_block_set(&inode, 0);
+ ext2fs_file_acl_block_set(fs, &inode, 0);
inode_modified++;
} else
not_fixed++;
not_fixed++;
}
- if (ext2fs_file_acl_block(&inode) &&
- ((ext2fs_file_acl_block(&inode) < fs->super->s_first_data_block) ||
- (ext2fs_file_acl_block(&inode) >= ext2fs_blocks_count(fs->super)))) {
+ if (ext2fs_file_acl_block(fs, &inode) &&
+ ((ext2fs_file_acl_block(fs, &inode) < fs->super->s_first_data_block) ||
+ (ext2fs_file_acl_block(fs, &inode) >= ext2fs_blocks_count(fs->super)))) {
if (fix_problem(ctx, PR_2_FILE_ACL_BAD, &pctx)) {
- ext2fs_file_acl_block_set(&inode, 0);
+ ext2fs_file_acl_block_set(fs, &inode, 0);
inode_modified++;
} else
not_fixed++;
* that was zeroed out and now needs to be replaced.
*/
static int allocate_dir_block(e2fsck_t ctx,
- struct ext2_db_entry *db,
+ struct ext2_db_entry2 *db,
char *buf EXT2FS_ATTR((unused)),
struct problem_context *pctx)
{