diff options
author | Yan, Zheng <zheng.yan@oracle.com> | 2009-11-12 04:36:34 -0500 |
---|---|---|
committer | Chris Mason <chris.mason@oracle.com> | 2009-12-17 12:33:35 -0500 |
commit | 24bbcf0442ee04660a5a030efdbb6d03f1c275cb (patch) | |
tree | aa57d77d29cc5150b272cc3f6465f10262fcbaac /fs/btrfs/transaction.c | |
parent | f34f57a3ab4e73304d78c125682f1a53cd3975f2 (diff) |
Btrfs: Add delayed iput
iput() can trigger new transactions if we are dropping the
final reference, so calling it in btrfs_commit_transaction
may end up deadlock. This patch adds delayed iput to avoid
the issue.
Signed-off-by: Yan Zheng <zheng.yan@oracle.com>
Signed-off-by: Chris Mason <chris.mason@oracle.com>
Diffstat (limited to 'fs/btrfs/transaction.c')
-rw-r--r-- | fs/btrfs/transaction.c | 13 |
1 files changed, 10 insertions, 3 deletions
diff --git a/fs/btrfs/transaction.c b/fs/btrfs/transaction.c index 728e8fe5d2cc..75b31caade29 100644 --- a/fs/btrfs/transaction.c +++ b/fs/btrfs/transaction.c | |||
@@ -333,6 +333,9 @@ static int __btrfs_end_transaction(struct btrfs_trans_handle *trans, | |||
333 | memset(trans, 0, sizeof(*trans)); | 333 | memset(trans, 0, sizeof(*trans)); |
334 | kmem_cache_free(btrfs_trans_handle_cachep, trans); | 334 | kmem_cache_free(btrfs_trans_handle_cachep, trans); |
335 | 335 | ||
336 | if (throttle) | ||
337 | btrfs_run_delayed_iputs(root); | ||
338 | |||
336 | return 0; | 339 | return 0; |
337 | } | 340 | } |
338 | 341 | ||
@@ -991,11 +994,11 @@ int btrfs_commit_transaction(struct btrfs_trans_handle *trans, | |||
991 | mutex_unlock(&root->fs_info->trans_mutex); | 994 | mutex_unlock(&root->fs_info->trans_mutex); |
992 | 995 | ||
993 | if (flush_on_commit) { | 996 | if (flush_on_commit) { |
994 | btrfs_start_delalloc_inodes(root); | 997 | btrfs_start_delalloc_inodes(root, 1); |
995 | ret = btrfs_wait_ordered_extents(root, 0); | 998 | ret = btrfs_wait_ordered_extents(root, 0, 1); |
996 | BUG_ON(ret); | 999 | BUG_ON(ret); |
997 | } else if (snap_pending) { | 1000 | } else if (snap_pending) { |
998 | ret = btrfs_wait_ordered_extents(root, 1); | 1001 | ret = btrfs_wait_ordered_extents(root, 0, 1); |
999 | BUG_ON(ret); | 1002 | BUG_ON(ret); |
1000 | } | 1003 | } |
1001 | 1004 | ||
@@ -1113,6 +1116,10 @@ int btrfs_commit_transaction(struct btrfs_trans_handle *trans, | |||
1113 | current->journal_info = NULL; | 1116 | current->journal_info = NULL; |
1114 | 1117 | ||
1115 | kmem_cache_free(btrfs_trans_handle_cachep, trans); | 1118 | kmem_cache_free(btrfs_trans_handle_cachep, trans); |
1119 | |||
1120 | if (current != root->fs_info->transaction_kthread) | ||
1121 | btrfs_run_delayed_iputs(root); | ||
1122 | |||
1116 | return ret; | 1123 | return ret; |
1117 | } | 1124 | } |
1118 | 1125 | ||