| From: Josef Bacik <josef@toxicpanda.com> |
| Date: Wed, 18 Dec 2019 17:20:29 -0500 |
| Subject: btrfs: do not delete mismatched root refs |
| |
| commit 423a716cd7be16fb08690760691befe3be97d3fc upstream. |
| |
| btrfs_del_root_ref() will simply WARN_ON() if the ref doesn't match in |
| any way, and then continue to delete the reference. This shouldn't |
| happen, we have these values because there's more to the reference than |
| the original root and the sub root. If any of these checks fail, return |
| -ENOENT. |
| |
| Signed-off-by: Josef Bacik <josef@toxicpanda.com> |
| Reviewed-by: David Sterba <dsterba@suse.com> |
| Signed-off-by: David Sterba <dsterba@suse.com> |
| Signed-off-by: Ben Hutchings <ben@decadent.org.uk> |
| --- |
| fs/btrfs/root-tree.c | 10 ++++++---- |
| 1 file changed, 6 insertions(+), 4 deletions(-) |
| |
| --- a/fs/btrfs/root-tree.c |
| +++ b/fs/btrfs/root-tree.c |
| @@ -373,11 +373,13 @@ again: |
| leaf = path->nodes[0]; |
| ref = btrfs_item_ptr(leaf, path->slots[0], |
| struct btrfs_root_ref); |
| - |
| - WARN_ON(btrfs_root_ref_dirid(leaf, ref) != dirid); |
| - WARN_ON(btrfs_root_ref_name_len(leaf, ref) != name_len); |
| ptr = (unsigned long)(ref + 1); |
| - WARN_ON(memcmp_extent_buffer(leaf, name, ptr, name_len)); |
| + if ((btrfs_root_ref_dirid(leaf, ref) != dirid) || |
| + (btrfs_root_ref_name_len(leaf, ref) != name_len) || |
| + memcmp_extent_buffer(leaf, name, ptr, name_len)) { |
| + err = -ENOENT; |
| + goto out; |
| + } |
| *sequence = btrfs_root_ref_sequence(leaf, ref); |
| |
| ret = btrfs_del_item(trans, tree_root, path); |