btrfs-progs: extent-tree: Add add_merge_cache_extent function

This add_merge_cache_extent() function will try to merge adjusted
cache_extent.

This is used for later btrfs-convert ext2 free space cache.

Signed-off-by: Qu Wenruo <quwenruo@cn.fujitsu.com>
Signed-off-by: David Sterba <dsterba@suse.com>
master
Qu Wenruo 2015-12-01 15:11:22 +08:00 committed by David Sterba
parent 466e066837
commit f735b37466
2 changed files with 65 additions and 0 deletions

View File

@ -282,3 +282,60 @@ void free_extent_cache_tree(struct cache_tree *tree)
{
cache_tree_free_extents(tree, free_extent_cache);
}
int add_merge_cache_extent(struct cache_tree *tree, u64 start, u64 size)
{
struct cache_extent *cache;
struct cache_extent *next = NULL;
struct cache_extent *prev = NULL;
int next_merged = 0;
int prev_merged = 0;
int ret = 0;
if (cache_tree_empty(tree))
goto insert;
cache = search_cache_extent(tree, start);
if (!cache) {
/*
* Either the tree is completely empty, or the no range after
* start.
* Either way, the last cache_extent should be prev.
*/
prev = last_cache_extent(tree);
} else if (start <= cache->start) {
next = cache;
prev = prev_cache_extent(cache);
} else {
prev = cache;
next = next_cache_extent(cache);
}
/*
* Ensure the range to be inserted won't cover with existings
* Or we will need extra loop to do merge
*/
BUG_ON(next && start + size > next->start);
BUG_ON(prev && prev->start + prev->size > start);
if (next && start + size == next->start) {
next_merged = 1;
next->size = next->start + next->size - start;
next->start = start;
}
if (prev && prev->start + prev->size == start) {
prev_merged = 1;
if (next_merged) {
next->size = next->start + next->size - prev->start;
next->start = prev->start;
remove_cache_extent(tree, prev);
free(prev);
} else {
prev->size = start + size - prev->start;
}
}
insert:
if (!prev_merged && !next_merged)
ret = add_cache_extent(tree, start, size);
return ret;
}

View File

@ -110,4 +110,12 @@ int add_cache_extent2(struct cache_tree *tree,
u64 objectid, u64 start, u64 size);
int insert_cache_extent2(struct cache_tree *tree, struct cache_extent *pe);
/*
* Insert a cache_extent range [start, start + size).
*
* This function may merge with existing cache_extent.
* NOTE: caller must ensure the inserted range won't cover with any existing
* range.
*/
int add_merge_cache_extent(struct cache_tree *tree, u64 start, u64 size);
#endif