* Copyright (C) 1993, 1994, 1995, 1996, 1997 Theodore Ts'o.
*
* %Begin-Header%
- * This file may be redistributed under the terms of the GNU Public
- * License.
+ * This file may be redistributed under the terms of the GNU Library
+ * General Public License, version 2.
* %End-Header%
*/
+#include "config.h"
#include <stdio.h>
#include <string.h>
#if HAVE_UNISTD_H
errcode_t magic;
ext2_filsys fs;
ext2_ino_t current_inode;
- blk_t current_block;
+ blk64_t current_block;
dgrp_t current_group;
ext2_ino_t inodes_left;
blk_t blocks_left;
scan->current_group = 0;
scan->groups_left = fs->group_desc_count - 1;
scan->inode_buffer_blocks = buffer_blocks ? buffer_blocks : 8;
- scan->current_block = scan->fs->
- group_desc[scan->current_group].bg_inode_table;
+ scan->current_block = ext2fs_inode_table_loc(scan->fs,
+ scan->current_group);
scan->inodes_left = EXT2_INODES_PER_GROUP(scan->fs->super);
scan->blocks_left = scan->fs->inode_blocks_per_group;
if (EXT2_HAS_RO_COMPAT_FEATURE(fs->super,
EXT4_FEATURE_RO_COMPAT_GDT_CSUM)) {
- scan->inodes_left -=
- fs->group_desc[scan->current_group].bg_itable_unused;
+ __u32 unused = ext2fs_bg_itable_unused(fs, scan->current_group);
+ if (scan->inodes_left > unused)
+ scan->inodes_left -= unused;
+ else
+ scan->inodes_left = 0;
scan->blocks_left =
(scan->inodes_left +
(fs->blocksize / scan->inode_size - 1)) *
scan->inode_size / fs->blocksize;
}
- retval = ext2fs_get_array(scan->inode_buffer_blocks,
- fs->blocksize,
- &scan->inode_buffer);
+ retval = io_channel_alloc_buf(fs->io, scan->inode_buffer_blocks,
+ &scan->inode_buffer);
scan->done_group = 0;
scan->done_group_data = 0;
scan->bad_block_ptr = 0;
scan->current_group++;
scan->groups_left--;
- scan->current_block =fs->group_desc[scan->current_group].bg_inode_table;
-
+ scan->current_block = ext2fs_inode_table_loc(scan->fs,
+ scan->current_group);
scan->current_inode = scan->current_group *
EXT2_INODES_PER_GROUP(fs->super);
scan->blocks_left = fs->inode_blocks_per_group;
if (EXT2_HAS_RO_COMPAT_FEATURE(fs->super,
EXT4_FEATURE_RO_COMPAT_GDT_CSUM)) {
- scan->inodes_left -=
- fs->group_desc[scan->current_group].bg_itable_unused;
+ __u32 unused = ext2fs_bg_itable_unused(fs, scan->current_group);
+ if (scan->inodes_left > unused)
+ scan->inodes_left -= unused;
+ else
+ scan->inodes_left = 0;
scan->blocks_left =
(scan->inodes_left +
(fs->blocksize / scan->inode_size - 1)) *
* increasing order.
*/
static errcode_t check_for_inode_bad_blocks(ext2_inode_scan scan,
- blk_t *num_blocks)
+ blk64_t *num_blocks)
{
- blk_t blk = scan->current_block;
+ blk64_t blk = scan->current_block;
badblocks_list bb = scan->fs->badblocks;
/*
*/
static errcode_t get_next_blocks(ext2_inode_scan scan)
{
- blk_t num_blocks;
+ blk64_t num_blocks;
errcode_t retval;
/*
memset(scan->inode_buffer, 0,
(size_t) num_blocks * scan->fs->blocksize);
} else {
- retval = io_channel_read_blk(scan->fs->io,
+ retval = io_channel_read_blk64(scan->fs->io,
scan->current_block,
(int) num_blocks,
scan->inode_buffer);
* they can be done for block group #0.
*/
if ((scan->scan_flags & EXT2_SF_DO_LAZY) &&
- (scan->fs->group_desc[scan->current_group].bg_flags &
- EXT2_BG_INODE_UNINIT))
+ (ext2fs_bg_flags_test(scan->fs, scan->current_group, EXT2_BG_INODE_UNINIT)
+ ))
goto force_new_group;
if (scan->inodes_left == 0)
goto force_new_group;
errcode_t ext2fs_read_inode_full(ext2_filsys fs, ext2_ino_t ino,
struct ext2_inode * inode, int bufsize)
{
- unsigned long group, block, block_nr, offset;
+ blk64_t block_nr;
+ unsigned long group, block, offset;
char *ptr;
errcode_t retval;
int clen, i, inodes_per_block, length;
EXT2_CHECK_MAGIC(fs, EXT2_ET_MAGIC_EXT2FS_FILSYS);
/* Check to see if user has an override function */
- if (fs->read_inode) {
+ if (fs->read_inode &&
+ ((bufsize == sizeof(struct ext2_inode)) ||
+ (EXT2_INODE_SIZE(fs->super) == sizeof(struct ext2_inode)))) {
retval = (fs->read_inode)(fs, ino, inode);
if (retval != EXT2_ET_CALLBACK_NOTHANDLED)
return retval;
offset = ((ino - 1) % EXT2_INODES_PER_GROUP(fs->super)) *
EXT2_INODE_SIZE(fs->super);
block = offset >> EXT2_BLOCK_SIZE_BITS(fs->super);
- if (!fs->group_desc[(unsigned)group].bg_inode_table)
+ if (!ext2fs_inode_table_loc(fs, (unsigned) group))
return EXT2_ET_MISSING_INODE_TABLE;
- block_nr = fs->group_desc[(unsigned)group].bg_inode_table +
+ block_nr = ext2fs_inode_table_loc(fs, group) +
block;
io = fs->io;
}
clen = fs->blocksize - offset;
if (block_nr != fs->icache->buffer_blk) {
- retval = io_channel_read_blk(io, block_nr, 1,
+ retval = io_channel_read_blk64(io, block_nr, 1,
fs->icache->buffer);
if (retval)
return retval;
errcode_t ext2fs_write_inode_full(ext2_filsys fs, ext2_ino_t ino,
struct ext2_inode * inode, int bufsize)
{
- unsigned long group, block, block_nr, offset;
+ blk64_t block_nr;
+ unsigned long group, block, offset;
errcode_t retval = 0;
struct ext2_inode_large temp_inode, *w_inode;
char *ptr;
if (length > (int) sizeof(struct ext2_inode_large)) {
w_inode = malloc(length);
- if (!w_inode)
- return ENOMEM;
+ if (!w_inode) {
+ retval = ENOMEM;
+ goto errout;
+ }
} else
w_inode = &temp_inode;
memset(w_inode, 0, length);
offset = ((ino - 1) % EXT2_INODES_PER_GROUP(fs->super)) *
EXT2_INODE_SIZE(fs->super);
block = offset >> EXT2_BLOCK_SIZE_BITS(fs->super);
- if (!fs->group_desc[(unsigned) group].bg_inode_table) {
+ if (!ext2fs_inode_table_loc(fs, (unsigned) group)) {
retval = EXT2_ET_MISSING_INODE_TABLE;
goto errout;
}
- block_nr = fs->group_desc[(unsigned) group].bg_inode_table + block;
+ block_nr = ext2fs_inode_table_loc(fs, (unsigned) group) + block;
offset &= (EXT2_BLOCK_SIZE(fs->super) - 1);
clen = fs->blocksize - offset;
if (fs->icache->buffer_blk != block_nr) {
- retval = io_channel_read_blk(fs->io, block_nr, 1,
+ retval = io_channel_read_blk64(fs->io, block_nr, 1,
fs->icache->buffer);
if (retval)
goto errout;
memcpy((char *) fs->icache->buffer + (unsigned) offset,
ptr, clen);
- retval = io_channel_write_blk(fs->io, block_nr, 1,
+ retval = io_channel_write_blk64(fs->io, block_nr, 1,
fs->icache->buffer);
if (retval)
goto errout;