Skip to content

Commit b28ff3a

Browse files
fdmananakdave
authored andcommitted
btrfs: check for commit error at btrfs_attach_transaction_barrier()
btrfs_attach_transaction_barrier() is used to get a handle pointing to the current running transaction if the transaction has not started its commit yet (its state is < TRANS_STATE_COMMIT_START). If the transaction commit has started, then we wait for the transaction to commit and finish before returning - however we completely ignore if the transaction was aborted due to some error during its commit, we simply return ERR_PT(-ENOENT), which makes the caller assume everything is fine and no errors happened. This could make an fsync return success (0) to user space when in fact we had a transaction abort and the target inode changes were therefore not persisted. Fix this by checking for the return value from btrfs_wait_for_commit(), and if it returned an error, return it back to the caller. Fixes: d4edf39 ("Btrfs: fix uncompleted transaction") CC: stable@vger.kernel.org # 4.19+ Reviewed-by: Qu Wenruo <wqu@suse.com> Signed-off-by: Filipe Manana <fdmanana@suse.com> Reviewed-by: David Sterba <dsterba@suse.com> Signed-off-by: David Sterba <dsterba@suse.com>
1 parent bf7ecbe commit b28ff3a

File tree

1 file changed

+7
-2
lines changed

1 file changed

+7
-2
lines changed

fs/btrfs/transaction.c

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -826,8 +826,13 @@ btrfs_attach_transaction_barrier(struct btrfs_root *root)
826826

827827
trans = start_transaction(root, 0, TRANS_ATTACH,
828828
BTRFS_RESERVE_NO_FLUSH, true);
829-
if (trans == ERR_PTR(-ENOENT))
830-
btrfs_wait_for_commit(root->fs_info, 0);
829+
if (trans == ERR_PTR(-ENOENT)) {
830+
int ret;
831+
832+
ret = btrfs_wait_for_commit(root->fs_info, 0);
833+
if (ret)
834+
return ERR_PTR(ret);
835+
}
831836

832837
return trans;
833838
}

0 commit comments

Comments
 (0)