Commit d13c94b9 authored by Tomasz Zawadzki's avatar Tomasz Zawadzki Committed by Jim Harris
Browse files

test/lvol: Test cases for lvs thin provisioning.

parent 628cd5e2
Loading
Loading
Loading
Loading
+2 −1
Original line number Diff line number Diff line
@@ -180,7 +180,8 @@ fi
if [ $SPDK_TEST_LVOL -eq 1 ]; then
	timing_enter lvol
	test_cases="1,50,51,52,53,100,101,102,250,251,252,253,255,"
	test_cases+="300,301,450,451,452,550,600,601,650,651,700"
	test_cases+="300,301,450,451,452,550,600,601,650,651,652,654,655,"
	test_cases+="700,701,750"
	run_test ./test/lvol/lvol.sh --test-cases=$test_cases
	timing_exit lvol
fi
+11 −3
Original line number Diff line number Diff line
@@ -50,9 +50,15 @@ function usage() {
                                    550: 'delete_bdev_positive',
                                    600: 'construct_lvol_store_with_cluster_size_max',
                                    601 'construct_lvol_store_with_cluster_size_min',
                                    650: 'tasting_positive',
                                    651: 'tasting_lvol_store_positive',
                                    700: 'SIGTERM'
                                    650: 'thin_provisioning_check_space',
                                    651: 'thin_provisioning_read_empty_bdev',
                                    652: 'thin_provisionind_data_integrity_test',
                                    653: 'thin_provisioning_resize',
                                    654: 'thin_overprovisioning',
                                    655: 'thin_provisioning_filling_disks_less_than_lvs_size',
                                    700: 'tasting_positive',
                                    701: 'tasting_lvol_store_positive',
                                    750: 'SIGTERM'
                                    or
                                    all: This parameter runs all tests
                                    Ex: \"1,2,19,20\", default: all"
@@ -85,6 +91,7 @@ source $TEST_DIR/scripts/autotest_common.sh
###  Function starts vhost app
function vhost_start()
{
    modprobe nbd
    touch $BASE_DIR/vhost.conf
    $TEST_DIR/scripts/gen_nvme.sh >> $BASE_DIR/vhost.conf
    $TEST_DIR/app/vhost/vhost -c $BASE_DIR/vhost.conf &
@@ -102,6 +109,7 @@ function vhost_kill()
    fi
    rm $BASE_DIR/vhost.pid || true
    rm $BASE_DIR/vhost.conf || true
    rmmod nbd || true
}

trap "vhost_kill; exit 1" SIGINT SIGTERM EXIT
+28 −4
Original line number Diff line number Diff line
@@ -101,14 +101,17 @@ class Commands_Rpc(object):
            "-c {cluster_sz}".format(cluster_sz=cluster_size))[0]
        return output.rstrip('\n')

    def construct_lvol_bdev(self, uuid, lbd_name, size):
    def construct_lvol_bdev(self, uuid, lbd_name, size, thin=False):
        print("INFO: RPC COMMAND construct_lvol_bdev")
        try:
            uuid_obj = UUID(uuid)
            name_opt = "-u"
        except ValueError:
            name_opt = "-l"
        output = self.rpc.construct_lvol_bdev(name_opt, uuid, lbd_name, size)[0]
        thin_provisioned = ""
        if thin:
            thin_provisioned = "-t"
        output = self.rpc.construct_lvol_bdev(name_opt, uuid, lbd_name, size, thin_provisioned)[0]
        return output.rstrip('\n')

    def destroy_lvol_store(self, uuid):
@@ -131,8 +134,21 @@ class Commands_Rpc(object):
        output, rc = self.rpc.resize_lvol_bdev(uuid, new_size)
        return rc

    def get_lvol_stores(self):
    def start_nbd_disk(self, bdev_name, nbd_name):
        print("INFO: RPC COMMAND start_nbd_disk")
        output, rc = self.rpc.start_nbd_disk(bdev_name, nbd_name)
        return rc

    def stop_nbd_disk(self, nbd_name):
        print("INFO: RPC COMMAND stop_nbd_disk")
        output, rc = self.rpc.stop_nbd_disk(nbd_name)
        return rc

    def get_lvol_stores(self, name=None):
        print("INFO: RPC COMMAND get_lvol_stores")
        if name:
            output = json.loads(self.rpc.get_lvol_stores("-l", name)[0])
        else:
            output = json.loads(self.rpc.get_lvol_stores()[0])
        return output

@@ -145,6 +161,14 @@ class Commands_Rpc(object):
                output.append(bdev)
        return output

    def get_lvol_bdev_with_name(self, name):
        print("INFO: RPC COMMAND get_bdevs; lvol bdevs only")
        rpc_output = json.loads(self.rpc.get_bdevs("-b", name)[0])
        if len(rpc_output) > 0:
            return rpc_output[0]

        return None

    def construct_nvme_bdev(self, nvme_name, trtype, traddr):
        print("INFO: Add NVMe bdev {nvme}".format(nvme=nvme_name))
        self.rpc.construct_nvme_bdev("-b", nvme_name, "-t", trtype, "-a", traddr)
+269 −11
Original line number Diff line number Diff line
@@ -14,11 +14,13 @@ from time import sleep
from uuid import uuid4


MEGABYTE = 1024 * 1024

def test_counter():
    '''
    :return: the number of tests
    '''
    return 24
    return 37


def header(num):
@@ -51,9 +53,15 @@ def header(num):
        550: 'delete_bdev_positive',
        600: 'construct_lvol_store_with_cluster_size_max',
        601: 'construct_lvol_store_with_cluster_size_min',
        650: 'tasting_positive',
        651: 'tasting_lvol_store_positive',
        700: 'SIGTERM',
        650: 'thin_provisioning_check_space',
        651: 'thin_provisioning_read_empty_bdev',
        652: 'thin_provisionind_data_integrity_test',
        653: 'thin_provisioning_resize',
        654: 'thin_overprovisioning',
        655: 'thin_provisioning_filling_disks_less_than_lvs_size',
        700: 'tasting_positive',
        701: 'tasting_lvol_store_positive',
        750: 'SIGTERM',
    }
    print("========================================================")
    print("Test Case {num}: Start".format(num=num))
@@ -83,6 +91,33 @@ class TestCases(object):
    def _gen_lvb_uudi(self):
        return "_".join([str(uuid4()), str(random.randrange(9999999999))])

    def run_fio_test(self, nbd_disk, offset, size, rw, pattern, expected_ret_value=0):
        fio_template = "fio --name=fio_test --filename=%(file)s --offset=%(offset)s --size=%(size)s"\
                       " --rw=%(rw)s --direct=1 %(pattern)s"
        pattern_template = ""
        if pattern:
            pattern_template = " --do_verify=1 --verify=pattern --verify_pattern=%s"\
                               " --verify_state_save=0" % pattern
        fio_cmd = fio_template % {"file": nbd_disk, "offset": offset, "size": size,
                                  "rw": rw, "pattern": pattern_template}
        try:
            output_fio = subprocess.check_output(fio_cmd, stderr=subprocess.STDOUT, shell=True)
            rv = 0
        except subprocess.CalledProcessError, ex:
            rv = 1
        except Exception as e:
            print("ERROR: Fio test ended with unexpected exception.")
            rv = 1

        if expected_ret_value == rv:
            return 0

        if rv == 0:
            print("ERROR: Fio test ended with unexpected success")
        else:
            print("ERROR: Fio test ended with unexpected failure")
        return 1

    def _stop_vhost(self, pid_path):
        with io.open(pid_path, 'r') as vhost_pid:
            pid = int(vhost_pid.readline())
@@ -679,6 +714,229 @@ class TestCases(object):

    def test_case650(self):
        header(650)
        base_name = self.c.construct_malloc_bdev(self.total_size,
                                                 self.block_size)
        uuid_store = self.c.construct_lvol_store(base_name,
                                                 self.lvs_name,
                                                 self.cluster_size)
        fail_count = self.c.check_get_lvol_stores(base_name, uuid_store,
                                                  self.cluster_size)
        lvs = self.c.get_lvol_stores(self.lvs_name)[0]
        free_clusters_start = int(lvs['free_clusters'])
        bdev_size = int(lvs['cluster_size']) * int(lvs['free_clusters']) / MEGABYTE
        bdev_name = self.c.construct_lvol_bdev(uuid_store, self.lbd_name,
                                               bdev_size, thin=True)
        lvs = self.c.get_lvol_stores(self.lvs_name)[0]
        free_clusters_create_lvol = int(lvs[u'free_clusters'])
        if free_clusters_start != free_clusters_create_lvol:
            fail_count += 1
        lvol_bdev = self.c.get_lvol_bdev_with_name(bdev_name)
        nbd_name = "/dev/nbd0"
        fail_count += self.c.start_nbd_disk(bdev_name, nbd_name)

        size = int(lvs['cluster_size'])
        fail_count += self.run_fio_test("/dev/nbd0", 0, size, "write", "0xcc")
        lvs = self.c.get_lvol_stores(self.lvs_name)[0]
        free_clusters_first_fio = int(lvs[u'free_clusters'])
        if free_clusters_start != free_clusters_first_fio + 1:
            fail_count += 1

        size = int(lvs['cluster_size'])
        # calculate size of one and half cluster
        offset = int((int(lvol_bdev['num_blocks']) * int(lvol_bdev['block_size']) /
                      free_clusters_create_lvol) * 1.5)
        fail_count += self.run_fio_test(nbd_name, offset, size, "write", "0xcc")
        lvs = self.c.get_lvol_stores(self.lvs_name)[0]
        free_clusters_second_fio = int(lvs[u'free_clusters'])
        if free_clusters_start != free_clusters_second_fio + 3:
            fail_count += 1

        size = (free_clusters_create_lvol - 3) * int(lvs['cluster_size'])
        offset = int(int(lvol_bdev['num_blocks']) * int(lvol_bdev['block_size']) /
                     free_clusters_create_lvol * 3)
        fail_count += self.run_fio_test(nbd_name, offset, size, "write", "0xcc")
        lvs = self.c.get_lvol_stores(self.lvs_name)[0]
        free_clusters_third_fio = int(lvs[u'free_clusters'])
        if free_clusters_third_fio != 0:
            fail_count += 1

        fail_count += self.c.stop_nbd_disk(nbd_name)
        fail_count += self.c.delete_bdev(lvol_bdev['name'])
        lvs = self.c.get_lvol_stores(self.lvs_name)[0]
        free_clusters_end = int(lvs[u'free_clusters'])
        if free_clusters_start != free_clusters_end:
            fail_count += 1
        fail_count += self.c.destroy_lvol_store(uuid_store)
        footer(650)
        return fail_count

    def test_case651(self):
        header(651)
        base_name = self.c.construct_malloc_bdev(self.total_size,
                                                 self.block_size)
        uuid_store = self.c.construct_lvol_store(base_name,
                                                 self.lvs_name,
                                                 self.cluster_size)
        fail_count = self.c.check_get_lvol_stores(base_name, uuid_store,
                                                  self.cluster_size)
        lvs = self.c.get_lvol_stores(self.lvs_name)[0]
        free_clusters_start = int(lvs['free_clusters'])
        lbd_name0 = self.lbd_name + str("0")
        lbd_name1 = self.lbd_name + str("1")
        # calculate bdev size in megabytes
        bdev_size = int(lvs['cluster_size']) * int(lvs['free_clusters']) / MEGABYTE
        bdev_name0 = self.c.construct_lvol_bdev(uuid_store, lbd_name0,
                                                bdev_size, thin=False)
        bdev_name1 = self.c.construct_lvol_bdev(uuid_store, lbd_name1,
                                                bdev_size, thin=True)
        lvol_bdev0 = self.c.get_lvol_bdev_with_name(bdev_name0)
        lvol_bdev1 = self.c.get_lvol_bdev_with_name(bdev_name1)
        nbd_name0 = "/dev/nbd0"
        fail_count += self.c.start_nbd_disk(lvol_bdev0['name'], nbd_name0)
        nbd_name1 = "/dev/nbd1"
        fail_count += self.c.start_nbd_disk(lvol_bdev1['name'], nbd_name1)

        size = bdev_size * MEGABYTE
        fail_count += self.run_fio_test(nbd_name0, 0, size, "write", False)

        size = bdev_size * MEGABYTE
        fail_count += self.run_fio_test(nbd_name1, 0, size, "read", "0x00")

        fail_count += self.c.stop_nbd_disk(nbd_name0)
        fail_count += self.c.stop_nbd_disk(nbd_name1)
        fail_count += self.c.delete_bdev(lvol_bdev0['name'])
        fail_count += self.c.delete_bdev(lvol_bdev1['name'])
        fail_count += self.c.destroy_lvol_store(uuid_store)
        footer(651)
        return fail_count

    def test_case652(self):
        header(652)
        base_name = self.c.construct_malloc_bdev(self.total_size,
                                                 self.block_size)
        uuid_store = self.c.construct_lvol_store(base_name,
                                                 self.lvs_name,
                                                 self.cluster_size)
        fail_count = self.c.check_get_lvol_stores(base_name, uuid_store,
                                                  self.cluster_size)
        lvs = self.c.get_lvol_stores(self.lvs_name)[0]
        free_clusters_start = int(lvs['free_clusters'])
        bdev_size = int(lvs['cluster_size']) * int(lvs['free_clusters']) / MEGABYTE
        bdev_name = self.c.construct_lvol_bdev(uuid_store, self.lbd_name,
                                               bdev_size, thin=True)

        lvol_bdev = self.c.get_lvol_bdev_with_name(bdev_name)
        nbd_name = "/dev/nbd0"
        fail_count += self.c.start_nbd_disk(lvol_bdev['name'], nbd_name)
        size = bdev_size * MEGABYTE
        fail_count += self.run_fio_test(nbd_name, 0, size, "write", "0xcc")

        fail_count += self.c.stop_nbd_disk(nbd_name)
        fail_count += self.c.delete_bdev(lvol_bdev['name'])
        fail_count += self.c.destroy_lvol_store(uuid_store)
        footer(652)
        return fail_count

    def test_case653(self):
        header(653)
        # TODO
        fail_count = 0
        footer(653)
        return fail_count

    def test_case654(self):
        header(654)
        base_name = self.c.construct_malloc_bdev(self.total_size,
                                                 self.block_size)
        uuid_store = self.c.construct_lvol_store(base_name, self.lvs_name,
                                                 self.cluster_size)
        fail_count = self.c.check_get_lvol_stores(base_name, uuid_store,
                                                  self.cluster_size)
        lvs = self.c.get_lvol_stores(self.lvs_name)[0]
        free_clusters_start = int(lvs['free_clusters'])
        lbd_name0 = self.lbd_name + str("0")
        lbd_name1 = self.lbd_name + str("1")
        bdev_size = int(lvs['cluster_size']) * int(lvs['free_clusters']) / MEGABYTE
        bdev_name0 = self.c.construct_lvol_bdev(uuid_store, lbd_name0,
                                                bdev_size, thin=True)
        bdev_name1 = self.c.construct_lvol_bdev(uuid_store, lbd_name1,
                                                bdev_size, thin=True)

        lvs = self.c.get_lvol_stores(self.lvs_name)[0]
        free_clusters_create_lvol = int(lvs[u'free_clusters'])
        if free_clusters_start != free_clusters_create_lvol:
            fail_count += 1
        lvol_bdev0 = self.c.get_lvol_bdev_with_name(bdev_name0)
        lvol_bdev1 = self.c.get_lvol_bdev_with_name(bdev_name1)

        nbd_name0 = "/dev/nbd0"
        nbd_name1 = "/dev/nbd1"
        fail_count += self.c.start_nbd_disk(lvol_bdev0['name'], nbd_name0)
        fail_count += self.c.start_nbd_disk(lvol_bdev1['name'], nbd_name1)

        size = "75%"
        fail_count += self.run_fio_test(nbd_name0, 0, size, "write", "0xcc")

        size = "75%"
        fail_count += self.run_fio_test(nbd_name1, 0, size, "write", "0xee",
                                        expected_ret_value=1)

        size = "75%"
        fail_count += self.run_fio_test(nbd_name0, 0, size, "read", "0xcc")

        size = "25%"
        offset = "75%"
        fail_count += self.run_fio_test(nbd_name0, offset, size, "read", "0x00")

        fail_count += self.c.stop_nbd_disk(nbd_name0)
        fail_count += self.c.stop_nbd_disk(nbd_name1)
        fail_count += self.c.delete_bdev(lvol_bdev0['name'])
        fail_count += self.c.delete_bdev(lvol_bdev1['name'])
        fail_count += self.c.destroy_lvol_store(uuid_store)
        footer(654)
        return fail_count

    def test_case655(self):
        header(655)
        base_name = self.c.construct_malloc_bdev(self.total_size,
                                                 self.block_size)
        uuid_store = self.c.construct_lvol_store(base_name, self.lvs_name,
                                                 self.cluster_size)
        fail_count = self.c.check_get_lvol_stores(base_name, uuid_store,
                                                  self.cluster_size)
        lvs = self.c.get_lvol_stores(self.lvs_name)[0]
        free_clusters_start = int(lvs['free_clusters'])
        lbd_name0 = self.lbd_name + str("0")
        lbd_name1 = self.lbd_name + str("1")
        lvs_size = int(lvs['cluster_size']) * int(lvs['free_clusters']) / MEGABYTE
        bdev_size = int(lvs_size * 0.7)
        bdev_name0 = self.c.construct_lvol_bdev(uuid_store, lbd_name0,
                                                bdev_size, thin=True)
        bdev_name1 = self.c.construct_lvol_bdev(uuid_store, lbd_name1,
                                                bdev_size, thin=True)

        lvol_bdev0 = self.c.get_lvol_bdev_with_name(bdev_name0)
        lvol_bdev1 = self.c.get_lvol_bdev_with_name(bdev_name1)

        nbd_name0 = "/dev/nbd0"
        nbd_name1 = "/dev/nbd1"
        fail_count += self.c.start_nbd_disk(lvol_bdev0['name'], nbd_name0)
        fail_count += self.c.start_nbd_disk(lvol_bdev1['name'], nbd_name1)
        size = int(int(lvol_bdev0['num_blocks']) * int(lvol_bdev0['block_size']) * 0.7)
        fail_count += self.run_fio_test(nbd_name0, 0, size, "write", "0xcc")
        size = int(int(lvol_bdev1['num_blocks']) * int(lvol_bdev1['block_size']) * 0.7)
        fail_count += self.run_fio_test(nbd_name1, 0, size, "write", "0xee")

        fail_count += self.c.stop_nbd_disk(nbd_name0)
        fail_count += self.c.stop_nbd_disk(nbd_name1)
        fail_count += self.c.delete_bdev(lvol_bdev0['name'])
        fail_count += self.c.delete_bdev(lvol_bdev1['name'])
        fail_count += self.c.destroy_lvol_store(uuid_store)
        footer(655)
        return fail_count

    def test_case700(self):
        header(700)
        fail_count = 0
        uuid_bdevs = []
        base_name = "Nvme0n1"
@@ -782,11 +1040,11 @@ class TestCases(object):
        if self.c.destroy_lvol_store(uuid_store) != 0:
            fail_count += 1

        footer(650)
        footer(700)
        return fail_count

    def test_case651(self):
        header(651)
    def test_case701(self):
        header(701)
        base_name = "Nvme0n1"
        uuid_store = self.c.construct_lvol_store(base_name,
                                                 self.lvs_name,
@@ -806,11 +1064,11 @@ class TestCases(object):
            fail_count += 1
        if self.c.destroy_lvol_store(uuid_store) != 0:
            fail_count += 1
        footer(651)
        footer(701)
        return fail_count

    def test_case700(self):
        header(700)
    def test_case750(self):
        header(750)
        pid_path = path.join(self.path, 'vhost.pid')

        base_name = self.c.construct_malloc_bdev(self.total_size,
@@ -822,5 +1080,5 @@ class TestCases(object):
                                                  self.cluster_size)

        fail_count += self._stop_vhost(pid_path)
        footer(700)
        footer(750)
        return fail_count