#!/usr/bin/env python3 # # Test incremental/backup across iothread contexts # # Copyright (c) 2019 John Snow for Red Hat, Inc. # # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 2 of the License, or # (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program. If not, see . # # owner=jsnow@redhat.com import os import iotests from iotests import log iotests.verify_image_format(supported_fmts=['qcow2']) size = 64 * 1024 * 1024 with iotests.FilePath('img0') as img0_path, \ iotests.FilePath('img1') as img1_path, \ iotests.FilePath('img0-full') as img0_full_path, \ iotests.FilePath('img1-full') as img1_full_path, \ iotests.FilePath('img0-incr') as img0_incr_path, \ iotests.FilePath('img1-incr') as img1_incr_path, \ iotests.VM() as vm: def create_target(filepath, name, size): basename = os.path.basename(filepath) nodename = "file_{}".format(basename) log(vm.command('blockdev-create', job_id='job1', options={ 'driver': 'file', 'filename': filepath, 'size': 0, })) vm.run_job('job1') log(vm.command('blockdev-add', driver='file', node_name=nodename, filename=filepath)) log(vm.command('blockdev-create', job_id='job2', options={ 'driver': iotests.imgfmt, 'file': nodename, 'size': size, })) vm.run_job('job2') log(vm.command('blockdev-add', driver=iotests.imgfmt, node_name=name, file=nodename)) log('--- Preparing images & VM ---\n') vm.add_object('iothread,id=iothread0') vm.add_object('iothread,id=iothread1') vm.add_device('virtio-scsi-pci,id=scsi0,iothread=iothread0') vm.add_device('virtio-scsi-pci,id=scsi1,iothread=iothread1') iotests.qemu_img_create('-f', iotests.imgfmt, img0_path, str(size)) iotests.qemu_img_create('-f', iotests.imgfmt, img1_path, str(size)) vm.add_drive(img0_path, interface='none') vm.add_device('scsi-hd,id=device0,drive=drive0,bus=scsi0.0') vm.add_drive(img1_path, interface='none') vm.add_device('scsi-hd,id=device1,drive=drive1,bus=scsi1.0') log('--- Starting VM ---\n') vm.launch() log('--- Create Targets & Full Backups ---\n') create_target(img0_full_path, 'img0-full', size) create_target(img1_full_path, 'img1-full', size) ret = vm.qmp_log('transaction', indent=2, actions=[ { 'type': 'block-dirty-bitmap-add', 'data': { 'node': 'drive0', 'name': 'bitmap0' }}, { 'type': 'block-dirty-bitmap-add', 'data': { 'node': 'drive1', 'name': 'bitmap1' }}, { 'type': 'blockdev-backup', 'data': { 'device': 'drive0', 'target': 'img0-full', 'sync': 'full', 'job-id': 'j0' }}, { 'type': 'blockdev-backup', 'data': { 'device': 'drive1', 'target': 'img1-full', 'sync': 'full', 'job-id': 'j1' }} ]) if "error" in ret: raise Exception(ret['error']['desc']) vm.run_job('j0', auto_dismiss=True) vm.run_job('j1', auto_dismiss=True) log('\n--- Create Targets & Incremental Backups ---\n') create_target(img0_incr_path, 'img0-incr', size) create_target(img1_incr_path, 'img1-incr', size) ret = vm.qmp_log('transaction', indent=2, actions=[ { 'type': 'blockdev-backup', 'data': { 'device': 'drive0', 'target': 'img0-incr', 'sync': 'incremental', 'bitmap': 'bitmap0', 'job-id': 'j2' }}, { 'type': 'blockdev-backup', 'data': { 'device': 'drive1', 'target': 'img1-incr', 'sync': 'incremental', 'bitmap': 'bitmap1', 'job-id': 'j3' }} ]) if "error" in ret: raise Exception(ret['error']['desc']) vm.run_job('j2', auto_dismiss=True) vm.run_job('j3', auto_dismiss=True) log('\n--- Done ---') vm.shutdown()