diff options
author | Josef Bacik <jbacik@fb.com> | 2014-11-21 20:52:38 +0100 |
---|---|---|
committer | Chris Mason <clm@fb.com> | 2014-11-21 20:58:32 +0100 |
commit | 50d9aa99bd35c77200e0e3dd7a72274f8304701f (patch) | |
tree | 346a80fdf2343a5c5e010b57b0213c989eed4ac8 /fs/btrfs/transaction.h | |
parent | Btrfs: make sure we wait on logged extents when fsycning two subvols (diff) | |
download | linux-50d9aa99bd35c77200e0e3dd7a72274f8304701f.tar.xz linux-50d9aa99bd35c77200e0e3dd7a72274f8304701f.zip |
Btrfs: make sure logged extents complete in the current transaction V3
Liu Bo pointed out that my previous fix would lose the generation update in the
scenario I described. It is actually much worse than that, we could lose the
entire extent if we lose power right after the transaction commits. Consider
the following
write extent 0-4k
log extent in log tree
commit transaction
< power fail happens here
ordered extent completes
We would lose the 0-4k extent because it hasn't updated the actual fs tree, and
the transaction commit will reset the log so it isn't replayed. If we lose
power before the transaction commit we are save, otherwise we are not.
Fix this by keeping track of all extents we logged in this transaction. Then
when we go to commit the transaction make sure we wait for all of those ordered
extents to complete before proceeding. This will make sure that if we lose
power after the transaction commit we still have our data. This also fixes the
problem of the improperly updated extent generation. Thanks,
cc: stable@vger.kernel.org
Signed-off-by: Josef Bacik <jbacik@fb.com>
Signed-off-by: Chris Mason <clm@fb.com>
Diffstat (limited to 'fs/btrfs/transaction.h')
-rw-r--r-- | fs/btrfs/transaction.h | 2 |
1 files changed, 2 insertions, 0 deletions
diff --git a/fs/btrfs/transaction.h b/fs/btrfs/transaction.h index b3f5b40aab22..fd400a3668a8 100644 --- a/fs/btrfs/transaction.h +++ b/fs/btrfs/transaction.h @@ -56,6 +56,7 @@ struct btrfs_transaction { wait_queue_head_t commit_wait; struct list_head pending_snapshots; struct list_head pending_chunks; + struct list_head pending_ordered; struct list_head switch_commits; struct btrfs_delayed_ref_root delayed_refs; int aborted; @@ -105,6 +106,7 @@ struct btrfs_trans_handle { */ struct btrfs_root *root; struct seq_list delayed_ref_elem; + struct list_head ordered; struct list_head qgroup_ref_list; struct list_head new_bgs; }; |