From: Theodore Ts'o Date: Mon, 2 Jun 2008 21:21:37 +0000 (-0400) Subject: libext2fs: Add callback functions for _alloc_block() and _block_alloc_stats() X-Git-Tag: v1.41-WIP-0617~30 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=f5c562e2324a8950d659ebfc8db4356121d6104e;p=thirdparty%2Fe2fsprogs.git libext2fs: Add callback functions for _alloc_block() and _block_alloc_stats() Add callback functions for ext2fs_alloc_block() and ext2fs_block_alloc_stats(). This is needed so e2fsck can be informed when the extent_set_bmap() function needs to allocate or deallocate blocks. Signed-off-by: "Theodore Ts'o" --- diff --git a/lib/ext2fs/alloc.c b/lib/ext2fs/alloc.c index 65f3ea1c3..f8d8a5fbb 100644 --- a/lib/ext2fs/alloc.c +++ b/lib/ext2fs/alloc.c @@ -118,15 +118,24 @@ errcode_t ext2fs_alloc_block(ext2_filsys fs, blk_t goal, } memset(block_buf, 0, fs->blocksize); - if (!fs->block_map) { - retval = ext2fs_read_block_bitmap(fs); + if (fs->get_alloc_block) { + blk64_t new; + + retval = (fs->get_alloc_block)(fs, (blk64_t) goal, &new); if (retval) goto fail; - } + block = (blk_t) new; + } else { + if (!fs->block_map) { + retval = ext2fs_read_block_bitmap(fs); + if (retval) + goto fail; + } - retval = ext2fs_new_block(fs, goal, 0, &block); - if (retval) - goto fail; + retval = ext2fs_new_block(fs, goal, 0, &block); + if (retval) + goto fail; + } retval = io_channel_write_blk(fs->io, block, 1, block_buf); if (retval) @@ -170,3 +179,19 @@ errcode_t ext2fs_get_free_blocks(ext2_filsys fs, blk_t start, blk_t finish, return EXT2_ET_BLOCK_ALLOC_FAIL; } +void ext2fs_set_alloc_block_callback(ext2_filsys fs, + errcode_t (*func)(ext2_filsys fs, + blk64_t goal, + blk64_t *ret), + errcode_t (**old)(ext2_filsys fs, + blk64_t goal, + blk64_t *ret)) +{ + if (!fs || fs->magic != EXT2_ET_MAGIC_EXT2FS_FILSYS) + return; + + if (old) + *old = fs->get_alloc_block; + + fs->get_alloc_block = func; +} diff --git a/lib/ext2fs/alloc_stats.c b/lib/ext2fs/alloc_stats.c index 3956528f9..a8514cc2e 100644 --- a/lib/ext2fs/alloc_stats.c +++ b/lib/ext2fs/alloc_stats.c @@ -69,4 +69,22 @@ void ext2fs_block_alloc_stats(ext2_filsys fs, blk_t blk, int inuse) fs->super->s_free_blocks_count -= inuse; ext2fs_mark_super_dirty(fs); ext2fs_mark_bb_dirty(fs); + if (fs->block_alloc_stats) + (fs->block_alloc_stats)(fs, (blk64_t) blk, inuse); +} + +void ext2fs_set_block_alloc_stats_callback(ext2_filsys fs, + void (*func)(ext2_filsys fs, + blk64_t blk, + int inuse), + void (**old)(ext2_filsys fs, + blk64_t blk, + int inuse)) +{ + if (!fs || fs->magic != EXT2_ET_MAGIC_EXT2FS_FILSYS) + return; + if (old) + *old = fs->block_alloc_stats; + + fs->block_alloc_stats = func; } diff --git a/lib/ext2fs/ext2fs.h b/lib/ext2fs/ext2fs.h index 3ef3b0dc2..ebad54e6a 100644 --- a/lib/ext2fs/ext2fs.h +++ b/lib/ext2fs/ext2fs.h @@ -229,6 +229,13 @@ struct struct_ext2_filsys { */ struct ext2_inode_cache *icache; io_channel image_io; + + /* + * More callback functions + */ + errcode_t (*get_alloc_block)(ext2_filsys fs, blk64_t goal, + blk64_t *ret); + void (*block_alloc_stats)(ext2_filsys fs, blk64_t blk, int inuse); }; #if EXT2_FLAT_INCLUDES @@ -552,11 +559,25 @@ extern errcode_t ext2fs_get_free_blocks(ext2_filsys fs, blk_t start, blk_t *ret); extern errcode_t ext2fs_alloc_block(ext2_filsys fs, blk_t goal, char *block_buf, blk_t *ret); +extern void ext2fs_set_alloc_block_callback(ext2_filsys fs, + errcode_t (*func)(ext2_filsys fs, + blk64_t goal, + blk64_t *ret), + errcode_t (**old)(ext2_filsys fs, + blk64_t goal, + blk64_t *ret)); /* alloc_sb.c */ extern int ext2fs_reserve_super_and_bgd(ext2_filsys fs, dgrp_t group, ext2fs_block_bitmap bmap); +extern void ext2fs_set_block_alloc_stats_callback(ext2_filsys fs, + void (*func)(ext2_filsys fs, + blk64_t blk, + int inuse), + void (**old)(ext2_filsys fs, + blk64_t blk, + int inuse)); /* alloc_stats.c */ void ext2fs_inode_alloc_stats(ext2_filsys fs, ext2_ino_t ino, int inuse);