btrfs: Support convert to -d dup for btrfs-convert
authorZhao Lei <zhaolei@cn.fujitsu.com>
Thu, 19 Nov 2015 09:26:22 +0000 (17:26 +0800)
committerDavid Sterba <dsterba@suse.com>
Thu, 7 Jan 2016 13:26:58 +0000 (14:26 +0100)
Since we will add support for -d dup for non-mixed filesystem,
kernel need to support converting to this raid-type.

This patch remove limitation of above case.

Tested by following script:
(combination of dup conversion with fsck):

export TEST_DEV='/dev/vdc'
export TEST_DIR='/var/ltf/tester/mnt'

do_dup_test()
{
    local m_from="$1"
    local d_from="$2"
    local m_to="$3"
    local d_to="$4"

    echo "Convert from -m $m_from -d $d_from to -m $m_to -d $d_to"

    umount "$TEST_DIR" &>/dev/null
    ./mkfs.btrfs -f -m "$m_from" -d "$d_from" "$TEST_DEV" >/dev/null || return 1
    mount "$TEST_DEV" "$TEST_DIR" || return 1

    cp -a /sbin/* "$TEST_DIR"

    [[ "$m_from" != "$m_to" ]] && {
        ./btrfs balance start -f -mconvert="$m_to" "$TEST_DIR" || return 1
    }

    [[ "$d_from" != "$d_to" ]] && {
local opt=()
[[ "$d_to" == single ]] && opt+=("-f")
        ./btrfs balance start "${opt[@]}" -dconvert="$d_to" "$TEST_DIR" || return 1
    }

    umount "$TEST_DIR" || return 1
    ./btrfsck "$TEST_DEV" || return 1
    echo

    return 0
}

test_all()
{
    for m_from in single dup; do
    for d_from in single dup; do
    for m_to in single dup; do
    for d_to in single dup; do
    do_dup_test "$m_from" "$d_from" "$m_to" "$d_to" || return 1
    done
    done
    done
    done
}

test_all

Signed-off-by: Zhao Lei <zhaolei@cn.fujitsu.com>
Reviewed-by: David Sterba <dsterba@suse.com>
Signed-off-by: David Sterba <dsterba@suse.com>
fs/btrfs/volumes.c

index a23399e8e3aba2f63d4c0cee90932d073d3bd113..33b02505d110ed5c3e443bdd90358fa33b2353ae 100644 (file)
@@ -3723,14 +3723,6 @@ int btrfs_balance(struct btrfs_balance_control *bctl,
                goto out;
        }
 
-       /* allow dup'ed data chunks only in mixed mode */
-       if (!mixed && (bctl->data.flags & BTRFS_BALANCE_ARGS_CONVERT) &&
-           (bctl->data.target & BTRFS_BLOCK_GROUP_DUP)) {
-               btrfs_err(fs_info, "dup for data is not allowed");
-               ret = -EINVAL;
-               goto out;
-       }
-
        /* allow to reduce meta or sys integrity only if force set */
        allowed = BTRFS_BLOCK_GROUP_DUP | BTRFS_BLOCK_GROUP_RAID1 |
                        BTRFS_BLOCK_GROUP_RAID10 |