mirror of
https://github.com/torvalds/linux.git
synced 2024-11-27 22:51:35 +00:00
btrfs: make tree iteration in extent_io_tree_release() more efficient
Currently extent_io_tree_release() is a loop that keeps getting the first node in the io tree, using rb_first() which is a loop that gets to the leftmost node of the rbtree, and then for each node it calls rb_erase(), which often requires rebalancing the rbtree. We can make this more efficient by using rbtree_postorder_for_each_entry_safe() to free each node without having to delete it from the rbtree and without looping to get the first node. Signed-off-by: Filipe Manana <fdmanana@suse.com> Reviewed-by: David Sterba <dsterba@suse.com> Signed-off-by: David Sterba <dsterba@suse.com>
This commit is contained in:
parent
df2a8e70c3
commit
63ffc1f7c4
@ -114,14 +114,15 @@ void extent_io_tree_init(struct btrfs_fs_info *fs_info,
|
||||
*/
|
||||
void extent_io_tree_release(struct extent_io_tree *tree)
|
||||
{
|
||||
spin_lock(&tree->lock);
|
||||
while (!RB_EMPTY_ROOT(&tree->state)) {
|
||||
struct rb_node *node;
|
||||
struct extent_state *state;
|
||||
struct rb_root root;
|
||||
struct extent_state *state;
|
||||
struct extent_state *tmp;
|
||||
|
||||
node = rb_first(&tree->state);
|
||||
state = rb_entry(node, struct extent_state, rb_node);
|
||||
rb_erase(&state->rb_node, &tree->state);
|
||||
spin_lock(&tree->lock);
|
||||
root = tree->state;
|
||||
tree->state = RB_ROOT;
|
||||
rbtree_postorder_for_each_entry_safe(state, tmp, &root, rb_node) {
|
||||
/* Clear node to keep free_extent_state() happy. */
|
||||
RB_CLEAR_NODE(&state->rb_node);
|
||||
ASSERT(!(state->state & EXTENT_LOCKED));
|
||||
/*
|
||||
@ -131,9 +132,13 @@ void extent_io_tree_release(struct extent_io_tree *tree)
|
||||
*/
|
||||
ASSERT(!waitqueue_active(&state->wq));
|
||||
free_extent_state(state);
|
||||
|
||||
cond_resched_lock(&tree->lock);
|
||||
}
|
||||
/*
|
||||
* Should still be empty even after a reschedule, no other task should
|
||||
* be accessing the tree anymore.
|
||||
*/
|
||||
ASSERT(RB_EMPTY_ROOT(&tree->state));
|
||||
spin_unlock(&tree->lock);
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user