xref: /qemu/tests/qemu-iotests/205 (revision 6dede6a493d245170e90f316883c966542f05bb5)
1903cb1bfSPhilippe Mathieu-Daudé#!/usr/bin/env python3
29dd003a9SVladimir Sementsov-Ogievskiy# group: rw quick
32dadedceSVladimir Sementsov-Ogievskiy#
42dadedceSVladimir Sementsov-Ogievskiy# Tests for qmp command nbd-server-remove.
52dadedceSVladimir Sementsov-Ogievskiy#
62dadedceSVladimir Sementsov-Ogievskiy# Copyright (c) 2017 Virtuozzo International GmbH
72dadedceSVladimir Sementsov-Ogievskiy#
82dadedceSVladimir Sementsov-Ogievskiy# This program is free software; you can redistribute it and/or modify
92dadedceSVladimir Sementsov-Ogievskiy# it under the terms of the GNU General Public License as published by
102dadedceSVladimir Sementsov-Ogievskiy# the Free Software Foundation; either version 2 of the License, or
112dadedceSVladimir Sementsov-Ogievskiy# (at your option) any later version.
122dadedceSVladimir Sementsov-Ogievskiy#
132dadedceSVladimir Sementsov-Ogievskiy# This program is distributed in the hope that it will be useful,
142dadedceSVladimir Sementsov-Ogievskiy# but WITHOUT ANY WARRANTY; without even the implied warranty of
152dadedceSVladimir Sementsov-Ogievskiy# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
162dadedceSVladimir Sementsov-Ogievskiy# GNU General Public License for more details.
172dadedceSVladimir Sementsov-Ogievskiy#
182dadedceSVladimir Sementsov-Ogievskiy# You should have received a copy of the GNU General Public License
192dadedceSVladimir Sementsov-Ogievskiy# along with this program.  If not, see <http://www.gnu.org/licenses/>.
202dadedceSVladimir Sementsov-Ogievskiy#
212dadedceSVladimir Sementsov-Ogievskiy
222dadedceSVladimir Sementsov-Ogievskiyimport os
232dadedceSVladimir Sementsov-Ogievskiyimport sys
242dadedceSVladimir Sementsov-Ogievskiyimport iotests
252dadedceSVladimir Sementsov-Ogievskiyimport time
2685a353a0SVladimir Sementsov-Ogievskiyfrom iotests import qemu_img_create, qemu_io, filter_qemu_io, QemuIoInteractive
272dadedceSVladimir Sementsov-Ogievskiy
282683ff77SMax Reitznbd_sock = os.path.join(iotests.sock_dir, 'nbd_sock')
292dadedceSVladimir Sementsov-Ogievskiynbd_uri = 'nbd+unix:///exp?socket=' + nbd_sock
302dadedceSVladimir Sementsov-Ogievskiydisk = os.path.join(iotests.test_dir, 'disk')
312dadedceSVladimir Sementsov-Ogievskiy
322dadedceSVladimir Sementsov-Ogievskiy
332dadedceSVladimir Sementsov-Ogievskiyclass TestNbdServerRemove(iotests.QMPTestCase):
342dadedceSVladimir Sementsov-Ogievskiy    def setUp(self):
3585a353a0SVladimir Sementsov-Ogievskiy        qemu_img_create('-f', iotests.imgfmt, disk, '1M')
362dadedceSVladimir Sementsov-Ogievskiy
372dadedceSVladimir Sementsov-Ogievskiy        self.vm = iotests.VM().add_drive(disk)
382dadedceSVladimir Sementsov-Ogievskiy        self.vm.launch()
392dadedceSVladimir Sementsov-Ogievskiy
402dadedceSVladimir Sementsov-Ogievskiy        address = {
412dadedceSVladimir Sementsov-Ogievskiy            'type': 'unix',
422dadedceSVladimir Sementsov-Ogievskiy            'data': {
432dadedceSVladimir Sementsov-Ogievskiy                'path': nbd_sock
442dadedceSVladimir Sementsov-Ogievskiy            }
452dadedceSVladimir Sementsov-Ogievskiy        }
462dadedceSVladimir Sementsov-Ogievskiy
472dadedceSVladimir Sementsov-Ogievskiy        result = self.vm.qmp('nbd-server-start', addr=address)
482dadedceSVladimir Sementsov-Ogievskiy        self.assert_qmp(result, 'return', {})
492dadedceSVladimir Sementsov-Ogievskiy        result = self.vm.qmp('nbd-server-add', device='drive0', name='exp')
502dadedceSVladimir Sementsov-Ogievskiy        self.assert_qmp(result, 'return', {})
512dadedceSVladimir Sementsov-Ogievskiy
522dadedceSVladimir Sementsov-Ogievskiy    def tearDown(self):
532dadedceSVladimir Sementsov-Ogievskiy        self.vm.shutdown()
542dadedceSVladimir Sementsov-Ogievskiy        os.remove(nbd_sock)
552dadedceSVladimir Sementsov-Ogievskiy        os.remove(disk)
562dadedceSVladimir Sementsov-Ogievskiy
572dadedceSVladimir Sementsov-Ogievskiy    def remove_export(self, name, mode=None):
582dadedceSVladimir Sementsov-Ogievskiy        if mode is None:
592dadedceSVladimir Sementsov-Ogievskiy            return self.vm.qmp('nbd-server-remove', name=name)
602dadedceSVladimir Sementsov-Ogievskiy        else:
612dadedceSVladimir Sementsov-Ogievskiy            return self.vm.qmp('nbd-server-remove', name=name, mode=mode)
622dadedceSVladimir Sementsov-Ogievskiy
632dadedceSVladimir Sementsov-Ogievskiy    def assertExportNotFound(self, name):
642dadedceSVladimir Sementsov-Ogievskiy        result = self.vm.qmp('nbd-server-remove', name=name)
652dadedceSVladimir Sementsov-Ogievskiy        self.assert_qmp(result, 'error/desc', "Export 'exp' is not found")
662dadedceSVladimir Sementsov-Ogievskiy
672dadedceSVladimir Sementsov-Ogievskiy    def assertExistingClients(self, result):
682dadedceSVladimir Sementsov-Ogievskiy        self.assert_qmp(result, 'error/desc', "export 'exp' still in use")
692dadedceSVladimir Sementsov-Ogievskiy
702dadedceSVladimir Sementsov-Ogievskiy    def assertReadOk(self, qemu_io_output):
712dadedceSVladimir Sementsov-Ogievskiy        self.assertEqual(
722dadedceSVladimir Sementsov-Ogievskiy                filter_qemu_io(qemu_io_output).strip(),
732dadedceSVladimir Sementsov-Ogievskiy                'read 512/512 bytes at offset 0\n' +
742dadedceSVladimir Sementsov-Ogievskiy                '512 bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)')
752dadedceSVladimir Sementsov-Ogievskiy
762dadedceSVladimir Sementsov-Ogievskiy    def assertReadFailed(self, qemu_io_output):
772dadedceSVladimir Sementsov-Ogievskiy        self.assertEqual(filter_qemu_io(qemu_io_output).strip(),
782dadedceSVladimir Sementsov-Ogievskiy                         'read failed: Input/output error')
792dadedceSVladimir Sementsov-Ogievskiy
802dadedceSVladimir Sementsov-Ogievskiy    def assertConnectFailed(self, qemu_io_output):
812dadedceSVladimir Sementsov-Ogievskiy        self.assertEqual(filter_qemu_io(qemu_io_output).strip(),
8236b9986bSThomas Huth                         "qemu-io: can't open device " + nbd_uri +
832dadedceSVladimir Sementsov-Ogievskiy                         ": Requested export not available\n"
842dadedceSVladimir Sementsov-Ogievskiy                         "server reported: export 'exp' not present")
852dadedceSVladimir Sementsov-Ogievskiy
862dadedceSVladimir Sementsov-Ogievskiy    def do_test_connect_after_remove(self, mode=None):
872dadedceSVladimir Sementsov-Ogievskiy        args = ('-r', '-f', 'raw', '-c', 'read 0 512', nbd_uri)
88*6dede6a4SJohn Snow        self.assertReadOk(qemu_io(*args).stdout)
892dadedceSVladimir Sementsov-Ogievskiy
902dadedceSVladimir Sementsov-Ogievskiy        result = self.remove_export('exp', mode)
912dadedceSVladimir Sementsov-Ogievskiy        self.assert_qmp(result, 'return', {})
922dadedceSVladimir Sementsov-Ogievskiy
932dadedceSVladimir Sementsov-Ogievskiy        self.assertExportNotFound('exp')
94*6dede6a4SJohn Snow        self.assertConnectFailed(qemu_io(*args, check=False).stdout)
952dadedceSVladimir Sementsov-Ogievskiy
962dadedceSVladimir Sementsov-Ogievskiy    def test_connect_after_remove_default(self):
972dadedceSVladimir Sementsov-Ogievskiy        self.do_test_connect_after_remove()
982dadedceSVladimir Sementsov-Ogievskiy
992dadedceSVladimir Sementsov-Ogievskiy    def test_connect_after_remove_safe(self):
1002dadedceSVladimir Sementsov-Ogievskiy        self.do_test_connect_after_remove('safe')
1012dadedceSVladimir Sementsov-Ogievskiy
1022dadedceSVladimir Sementsov-Ogievskiy    def test_connect_after_remove_force(self):
1032dadedceSVladimir Sementsov-Ogievskiy        self.do_test_connect_after_remove('hard')
1042dadedceSVladimir Sementsov-Ogievskiy
1052dadedceSVladimir Sementsov-Ogievskiy    def do_test_remove_during_connect_safe(self, mode=None):
1062dadedceSVladimir Sementsov-Ogievskiy        qio = QemuIoInteractive('-r', '-f', 'raw', nbd_uri)
1072dadedceSVladimir Sementsov-Ogievskiy        self.assertReadOk(qio.cmd('read 0 512'))
1082dadedceSVladimir Sementsov-Ogievskiy
1092dadedceSVladimir Sementsov-Ogievskiy        result = self.remove_export('exp', mode)
1102dadedceSVladimir Sementsov-Ogievskiy        self.assertExistingClients(result)
1112dadedceSVladimir Sementsov-Ogievskiy
1122dadedceSVladimir Sementsov-Ogievskiy        self.assertReadOk(qio.cmd('read 0 512'))
1132dadedceSVladimir Sementsov-Ogievskiy
1142dadedceSVladimir Sementsov-Ogievskiy        qio.close()
1152dadedceSVladimir Sementsov-Ogievskiy
1162dadedceSVladimir Sementsov-Ogievskiy        result = self.remove_export('exp', mode)
1172dadedceSVladimir Sementsov-Ogievskiy        self.assert_qmp(result, 'return', {})
1182dadedceSVladimir Sementsov-Ogievskiy
1192dadedceSVladimir Sementsov-Ogievskiy        self.assertExportNotFound('exp')
1202dadedceSVladimir Sementsov-Ogievskiy
1212dadedceSVladimir Sementsov-Ogievskiy    def test_remove_during_connect_default(self):
1222dadedceSVladimir Sementsov-Ogievskiy        self.do_test_remove_during_connect_safe()
1232dadedceSVladimir Sementsov-Ogievskiy
1242dadedceSVladimir Sementsov-Ogievskiy    def test_remove_during_connect_safe(self):
1252dadedceSVladimir Sementsov-Ogievskiy        self.do_test_remove_during_connect_safe('safe')
1262dadedceSVladimir Sementsov-Ogievskiy
1272dadedceSVladimir Sementsov-Ogievskiy    def test_remove_during_connect_hard(self):
1282dadedceSVladimir Sementsov-Ogievskiy        qio = QemuIoInteractive('-r', '-f', 'raw', nbd_uri)
1292dadedceSVladimir Sementsov-Ogievskiy        self.assertReadOk(qio.cmd('read 0 512'))
1302dadedceSVladimir Sementsov-Ogievskiy
1312dadedceSVladimir Sementsov-Ogievskiy        result = self.remove_export('exp', 'hard')
1322dadedceSVladimir Sementsov-Ogievskiy        self.assert_qmp(result, 'return', {})
1332dadedceSVladimir Sementsov-Ogievskiy
1342dadedceSVladimir Sementsov-Ogievskiy        self.assertReadFailed(qio.cmd('read 0 512'))
1352dadedceSVladimir Sementsov-Ogievskiy        self.assertExportNotFound('exp')
1362dadedceSVladimir Sementsov-Ogievskiy
1372dadedceSVladimir Sementsov-Ogievskiy        qio.close()
1382dadedceSVladimir Sementsov-Ogievskiy
1392dadedceSVladimir Sementsov-Ogievskiy    def test_remove_during_connect_safe_hard(self):
1402dadedceSVladimir Sementsov-Ogievskiy        qio = QemuIoInteractive('-r', '-f', 'raw', nbd_uri)
1412dadedceSVladimir Sementsov-Ogievskiy        self.assertReadOk(qio.cmd('read 0 512'))
1422dadedceSVladimir Sementsov-Ogievskiy
1432dadedceSVladimir Sementsov-Ogievskiy        result = self.remove_export('exp', 'safe')
1442dadedceSVladimir Sementsov-Ogievskiy        self.assertExistingClients(result)
1452dadedceSVladimir Sementsov-Ogievskiy
1462dadedceSVladimir Sementsov-Ogievskiy        self.assertReadOk(qio.cmd('read 0 512'))
1472dadedceSVladimir Sementsov-Ogievskiy
1482dadedceSVladimir Sementsov-Ogievskiy        result = self.remove_export('exp', 'hard')
1492dadedceSVladimir Sementsov-Ogievskiy        self.assert_qmp(result, 'return', {})
1502dadedceSVladimir Sementsov-Ogievskiy
1512dadedceSVladimir Sementsov-Ogievskiy        self.assertExportNotFound('exp')
1522dadedceSVladimir Sementsov-Ogievskiy        self.assertReadFailed(qio.cmd('read 0 512'))
1532dadedceSVladimir Sementsov-Ogievskiy        qio.close()
1542dadedceSVladimir Sementsov-Ogievskiy
1552dadedceSVladimir Sementsov-Ogievskiy
1562dadedceSVladimir Sementsov-Ogievskiyif __name__ == '__main__':
1577c932a1dSMax Reitz    iotests.main(supported_fmts=['raw'],
1587c932a1dSMax Reitz                 supported_protocols=['nbd'])
159