diff options
author | Yan, Zheng <zheng.yan@oracle.com> | 2010-05-16 10:49:59 -0400 |
---|---|---|
committer | Chris Mason <chris.mason@oracle.com> | 2010-05-25 10:34:54 -0400 |
commit | 3fd0a5585eb98e074fb9934549c8d85c49756c0d (patch) | |
tree | 3e7ff9bd9678a5eea62818a2f4a50e19dda91a81 /fs/btrfs/extent-tree.c | |
parent | efa56464562991b8c24f965199888806bd8c4b38 (diff) |
Btrfs: Metadata ENOSPC handling for balance
This patch adds metadata ENOSPC handling for the balance code.
It is consisted by following major changes:
1. Avoid COW tree leave in the phrase of merging tree.
2. Handle interaction with snapshot creation.
3. make the backref cache can live across transactions.
Signed-off-by: Yan Zheng <zheng.yan@oracle.com>
Signed-off-by: Chris Mason <chris.mason@oracle.com>
Diffstat (limited to 'fs/btrfs/extent-tree.c')
-rw-r--r-- | fs/btrfs/extent-tree.c | 23 |
1 files changed, 9 insertions, 14 deletions
diff --git a/fs/btrfs/extent-tree.c b/fs/btrfs/extent-tree.c index a713f69f0c7a..d61a799fe323 100644 --- a/fs/btrfs/extent-tree.c +++ b/fs/btrfs/extent-tree.c | |||
@@ -5875,7 +5875,8 @@ static noinline int walk_up_tree(struct btrfs_trans_handle *trans, | |||
5875 | * also make sure backrefs for the shared block and all lower level | 5875 | * also make sure backrefs for the shared block and all lower level |
5876 | * blocks are properly updated. | 5876 | * blocks are properly updated. |
5877 | */ | 5877 | */ |
5878 | int btrfs_drop_snapshot(struct btrfs_root *root, int update_ref) | 5878 | int btrfs_drop_snapshot(struct btrfs_root *root, |
5879 | struct btrfs_block_rsv *block_rsv, int update_ref) | ||
5879 | { | 5880 | { |
5880 | struct btrfs_path *path; | 5881 | struct btrfs_path *path; |
5881 | struct btrfs_trans_handle *trans; | 5882 | struct btrfs_trans_handle *trans; |
@@ -5894,6 +5895,8 @@ int btrfs_drop_snapshot(struct btrfs_root *root, int update_ref) | |||
5894 | BUG_ON(!wc); | 5895 | BUG_ON(!wc); |
5895 | 5896 | ||
5896 | trans = btrfs_start_transaction(tree_root, 0); | 5897 | trans = btrfs_start_transaction(tree_root, 0); |
5898 | if (block_rsv) | ||
5899 | trans->block_rsv = block_rsv; | ||
5897 | 5900 | ||
5898 | if (btrfs_disk_key_objectid(&root_item->drop_progress) == 0) { | 5901 | if (btrfs_disk_key_objectid(&root_item->drop_progress) == 0) { |
5899 | level = btrfs_header_level(root->node); | 5902 | level = btrfs_header_level(root->node); |
@@ -5981,24 +5984,16 @@ int btrfs_drop_snapshot(struct btrfs_root *root, int update_ref) | |||
5981 | } | 5984 | } |
5982 | 5985 | ||
5983 | BUG_ON(wc->level == 0); | 5986 | BUG_ON(wc->level == 0); |
5984 | if (trans->transaction->in_commit || | 5987 | if (btrfs_should_end_transaction(trans, tree_root)) { |
5985 | trans->transaction->delayed_refs.flushing) { | ||
5986 | ret = btrfs_update_root(trans, tree_root, | 5988 | ret = btrfs_update_root(trans, tree_root, |
5987 | &root->root_key, | 5989 | &root->root_key, |
5988 | root_item); | 5990 | root_item); |
5989 | BUG_ON(ret); | 5991 | BUG_ON(ret); |
5990 | 5992 | ||
5991 | btrfs_end_transaction(trans, tree_root); | 5993 | btrfs_end_transaction_throttle(trans, tree_root); |
5992 | trans = btrfs_start_transaction(tree_root, 0); | 5994 | trans = btrfs_start_transaction(tree_root, 0); |
5993 | if (IS_ERR(trans)) | 5995 | if (block_rsv) |
5994 | return PTR_ERR(trans); | 5996 | trans->block_rsv = block_rsv; |
5995 | } else { | ||
5996 | unsigned long update; | ||
5997 | update = trans->delayed_ref_updates; | ||
5998 | trans->delayed_ref_updates = 0; | ||
5999 | if (update) | ||
6000 | btrfs_run_delayed_refs(trans, tree_root, | ||
6001 | update); | ||
6002 | } | 5997 | } |
6003 | } | 5998 | } |
6004 | btrfs_release_path(root, path); | 5999 | btrfs_release_path(root, path); |
@@ -6026,7 +6021,7 @@ int btrfs_drop_snapshot(struct btrfs_root *root, int update_ref) | |||
6026 | kfree(root); | 6021 | kfree(root); |
6027 | } | 6022 | } |
6028 | out: | 6023 | out: |
6029 | btrfs_end_transaction(trans, tree_root); | 6024 | btrfs_end_transaction_throttle(trans, tree_root); |
6030 | kfree(wc); | 6025 | kfree(wc); |
6031 | btrfs_free_path(path); | 6026 | btrfs_free_path(path); |
6032 | return err; | 6027 | return err; |