On 09/20/2012 02:58 PM, Miroslav Rezanina wrote:
Test block mirroring

This test verify block mirroring functionality in qemu. Tested are following 
scenarios:

1) Original mage is synchronized into a mirrored one and when synchronization
    is done, switch to mirrored image is verified and content of both images
    is compared.

2) Continue in mirroring after disk synchronization. Verify the changes done
    are properly mirrored.

This test has following requirement for qemu:
- block mirroring has to be supported
- compare command for qemu-img has to be implemented

This requirements are not included in qemu upstream yet. You can get version
with required features In repository git://github.com/LaneWolf/qemu.git on 
branch blockjobs-1.2

Signed-off-by: Miroslav Rezanina <[email protected]>

Patch:
--
diff --git a/client/tests/virt/kvm/tests/block_mirror.py 
b/client/tests/virt/kvm/tests/block_mirror.py
new file mode 100644
index 0000000..a5bfdbb
--- /dev/null
+++ b/client/tests/virt/kvm/tests/block_mirror.py
@@ -0,0 +1,149 @@
+import re, os, logging, time
+from autotest.client.shared import utils, error
+from autotest.client.virt import kvm_monitor, virt_storage
+from autotest.client.virt import virt_env_process
+
+
[email protected]_aware
+def run_block_mirror(test, params, env):
+    """
+    Test block mirroring functionality
+
+    Test consists of two subtests:
+    1) Mirror the guest and switch to the mirrored one
+    2) Synchronize disk and then do continuous backup
+
+    "qemu-img compare" is used to verify disk is mirrored successfully.
+    """
+    image_name = params.get("image_name", "image")
+    image_format = params.get("image_format","qcow2")
+    image_orig = "%s.%s" % (image_name, image_format)
+    image_mirror = "%s-mirror.%s" % (image_name, image_format)
+    drive_format = params.get("drive_format")
+    block_mirror_cmd = params.get("block_mirror_cmd","drive-mirror")
+    device_id = "None"
+    qemu_img = params.get("qemu_img_binary")
+
+
+    def check_block_jobs_info():
+        """
+        Verify the status of block-jobs reported by monitor command info 
block-jobs.
+        @return: parsed output of info block-jobs

Lucas, it makes sense to have a generic function that will check for the required capabilities each tests needs prior to its execution.

Btw: Was this patch reviewed?

Thanks,
Dor

+        """
+        fail = 0
+
+        try:
+            output = vm.monitor.info("block-jobs")
+        except kvm_monitor.MonitorError, e:
+            logging.error(e)
+            fail += 1
+            return None, None
+        return (re.match("[\w ]+", str(output)), re.findall("\d+", 
str(output)))
+
+
+    def run_mirroring(vm, cmd, device, dest, complete = True):
+        """
+        Run block mirroring.
+
+        @param vm: Virtual machine object
+        @param cmd: Command for start mirroring
+        @param device: Guest device that has to be mirrored
+        @param dest: Location image has to be mirrored into
+        @param complete: If True, mirroring will complete (switch to mirror),
+                         If False, finish image synchronization and keep
+                         mirroring running (any changes will be mirrored)
+        """
+        vm.monitor.cmd("%s %s %s" % (cmd, device, dest))
+
+        while True:
+            blkjobout, blkjobstatus = check_block_jobs_info()
+            if 'mirror' in blkjobout.group(0):
+                logging.info("[(Completed bytes): %s (Total bytes): %s "
+                             "(Speed in bytes/s): %s]", blkjobstatus[-3],
+                             blkjobstatus[-2], blkjobstatus[-1])
+                if int(blkjobstatus[-3]) != int(blkjobstatus[-2]):
+                    time.sleep(10)
+                    continue
+                else:
+                    logging.info("Target synchronized with source")
+                    if complete:
+                        logging.info("Start mirroring completing")
+                        vm.monitor.cmd("stop")
+                        vm.monitor.cmd("block_job_complete %s" % device)
+                        time.sleep(5)
+                    else:
+                        break
+            elif 'No' in blkjobout.group(0):
+                logging.info("Block job completed")
+                break
+
+
+    def compare_images(cmd, img1, img2):
+        """
+        Check if images are equal. Raise error.TestFail if images not equal.
+
+        @param cmd: qemu-img executable
+        @param img1: First image to compare
+        @param img2: Second image to compare
+
+        """
+        logging.info("Comparing images")
+        compare_cmd = "%s compare %s %s" % (cmd, img1, img2)
+        rv = utils.run(compare_cmd, ignore_status=True)
+
+        if rv.exit_status == 0:
+            logging.info("Images are equal")
+        elif rv.exit_status == 1:
+            raise error.TestFail("Images differ - test failed")
+        else:
+            raise error.TestError("Error when compare images")
+
+
+    try:
+        # Setup phase
+        vm_name = params.get('main_vm')
+        virt_env_process.preprocess_vm(test, params, env, vm_name)
+        vm = env.get_vm(vm_name)
+        vm.create()
+
+        timeout = int(params.get("login_timeout", 360))
+        session = vm.wait_for_login(timeout=timeout)
+        img_path = virt_storage.get_image_filename(params, vm.root_dir)
+
+        if 'ide' in drive_format:
+            device_id = " id0-hd0"
+        elif 'virtio' in drive_format:
+            device_id = " virtio0"
+        else:
+            raise error.TestError("The drive format is not supported")
+
+        # Subtest 1 - Complete mirroring
+        error.context("Testing complete mirroring")
+        run_mirroring(vm,block_mirror_cmd, device_id, image_mirror)
+        output = vm.monitor.info("block")
+        if image_orig in output or image_mirror not in output:
+            raise error.TestError("Mirrored image not used by guest")
+        error.context("Compare fully mirrored images")
+        compare_images(qemu_img, img_path, image_mirror)
+        vm.destroy()
+
+        # Subtest 2 - Continuous backup
+        error.context("Testing continuous backup")
+        vm.create()
+        session = vm.wait_for_login(timeout=timeout)
+        run_mirroring(vm,block_mirror_cmd, device_id, image_mirror,False)
+        if image_orig in output or image_mirror not in output:
+            raise error.TestError("Mirrored image not used by guest")
+        for fn in range(0,128):
+            session.cmd("dd bs=1024 count=1024 if=/dev/urandom of=tmp%d.file"
+                        % fn)
+        time.sleep(10)
+        vm.monitor.cmd("stop")
+        time.sleep(5)
+        error.context("Compare original and backup images")
+        compare_images(qemu_img, img_path, image_mirror)
+        vm.destroy()
+
+    finally:
+        if os.path.isfile(image_mirror):
+            os.remove(image_mirror)
diff --git a/client/tests/virt/shared/cfg/subtests.cfg.sample 
b/client/tests/virt/shared/cfg/subtests.cfg.sample
index 921276b..33f9884 100644
--- a/client/tests/virt/shared/cfg/subtests.cfg.sample
+++ b/client/tests/virt/shared/cfg/subtests.cfg.sample
@@ -1132,6 +1132,10 @@ variants:
          type = block_stream
          alive_test_cmd = uname -a

+    - block_mirror:
+        type = block_mirror
+        block_mirror_cmd = drive_mirror
+
      - stop_continue: install setup image_copy unattended_install.cdrom
          type = stop_continue
          kill_vm_on_error = yes


_______________________________________________
Autotest-kernel mailing list
[email protected]
https://www.redhat.com/mailman/listinfo/autotest-kernel

Reply via email to