aboutsummaryrefslogtreecommitdiffstats
path: root/fs/btrfs/backref.c
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2012-07-05 16:06:25 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2012-07-05 16:06:25 -0400
commit5eecb9cc9029aef3c308fc94149c4a3065d40d9a (patch)
treeb5a7f7bf298ef0efc4ff5577b9a6a4dcec3db028 /fs/btrfs/backref.c
parent62ad64498a2e72eb9fb70ab80e20ecc9cac8d40b (diff)
parentb6305567e7d31b0bec1b8cb9ec0cadd7f7086f5f (diff)
Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/mason/linux-btrfs
Pull btrfs updates from Chris Mason: "I held off on my rc5 pull because I hit an oops during log recovery after a crash. I wanted to make sure it wasn't a regression because we have some logging fixes in here. It turns out that a commit during the merge window just made it much more likely to trigger directory logging instead of full commits, which exposed an old bug. The new backref walking code got some additional fixes. This should be the final set of them. Josef fixed up a corner where our O_DIRECT writes and buffered reads could expose old file contents (not stale, just not the most recent). He and Liu Bo fixed crashes during tree log recover as well. Ilya fixed errors while we resume disk balancing operations on readonly mounts." * 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/mason/linux-btrfs: Btrfs: run delayed directory updates during log replay Btrfs: hold a ref on the inode during writepages Btrfs: fix tree log remove space corner case Btrfs: fix wrong check during log recovery Btrfs: use _IOR for BTRFS_IOC_SUBVOL_GETFLAGS Btrfs: resume balance on rw (re)mounts properly Btrfs: restore restriper state on all mounts Btrfs: fix dio write vs buffered read race Btrfs: don't count I/O statistic read errors for missing devices Btrfs: resolve tree mod log locking issue in btrfs_next_leaf Btrfs: fix tree mod log rewind of ADD operations Btrfs: leave critical region in btrfs_find_all_roots as soon as possible Btrfs: always put insert_ptr modifications into the tree mod log Btrfs: fix tree mod log for root replacements at leaf level Btrfs: support root level changes in __resolve_indirect_ref Btrfs: avoid waiting for delayed refs when we must not
Diffstat (limited to 'fs/btrfs/backref.c')
-rw-r--r--fs/btrfs/backref.c15
1 files changed, 9 insertions, 6 deletions
diff --git a/fs/btrfs/backref.c b/fs/btrfs/backref.c
index 7301cdb4b2cb..a383c18e74e8 100644
--- a/fs/btrfs/backref.c
+++ b/fs/btrfs/backref.c
@@ -301,10 +301,14 @@ static int __resolve_indirect_ref(struct btrfs_fs_info *fs_info,
301 goto out; 301 goto out;
302 302
303 eb = path->nodes[level]; 303 eb = path->nodes[level];
304 if (!eb) { 304 while (!eb) {
305 WARN_ON(1); 305 if (!level) {
306 ret = 1; 306 WARN_ON(1);
307 goto out; 307 ret = 1;
308 goto out;
309 }
310 level--;
311 eb = path->nodes[level];
308 } 312 }
309 313
310 ret = add_all_parents(root, path, parents, level, &ref->key_for_search, 314 ret = add_all_parents(root, path, parents, level, &ref->key_for_search,
@@ -835,6 +839,7 @@ again:
835 } 839 }
836 ret = __add_delayed_refs(head, delayed_ref_seq, 840 ret = __add_delayed_refs(head, delayed_ref_seq,
837 &prefs_delayed); 841 &prefs_delayed);
842 mutex_unlock(&head->mutex);
838 if (ret) { 843 if (ret) {
839 spin_unlock(&delayed_refs->lock); 844 spin_unlock(&delayed_refs->lock);
840 goto out; 845 goto out;
@@ -928,8 +933,6 @@ again:
928 } 933 }
929 934
930out: 935out:
931 if (head)
932 mutex_unlock(&head->mutex);
933 btrfs_free_path(path); 936 btrfs_free_path(path);
934 while (!list_empty(&prefs)) { 937 while (!list_empty(&prefs)) {
935 ref = list_first_entry(&prefs, struct __prelim_ref, list); 938 ref = list_first_entry(&prefs, struct __prelim_ref, list);