xref: /OK3568_Linux_fs/yocto/poky/meta/lib/oeqa/selftest/cases/runqemu.py (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun#
2*4882a593Smuzhiyun# Copyright (c) 2017 Wind River Systems, Inc.
3*4882a593Smuzhiyun#
4*4882a593Smuzhiyun# SPDX-License-Identifier: MIT
5*4882a593Smuzhiyun#
6*4882a593Smuzhiyun
7*4882a593Smuzhiyunimport re
8*4882a593Smuzhiyunimport tempfile
9*4882a593Smuzhiyunimport time
10*4882a593Smuzhiyunimport oe.types
11*4882a593Smuzhiyunfrom oeqa.core.decorator import OETestTag
12*4882a593Smuzhiyunfrom oeqa.selftest.case import OESelftestTestCase
13*4882a593Smuzhiyunfrom oeqa.utils.commands import bitbake, runqemu, get_bb_var, runCmd
14*4882a593Smuzhiyun
15*4882a593Smuzhiyun@OETestTag("runqemu")
16*4882a593Smuzhiyunclass RunqemuTests(OESelftestTestCase):
17*4882a593Smuzhiyun    """Runqemu test class"""
18*4882a593Smuzhiyun
19*4882a593Smuzhiyun    image_is_ready = False
20*4882a593Smuzhiyun    deploy_dir_image = ''
21*4882a593Smuzhiyun
22*4882a593Smuzhiyun    def setUpLocal(self):
23*4882a593Smuzhiyun        super(RunqemuTests, self).setUpLocal()
24*4882a593Smuzhiyun        self.recipe = 'core-image-minimal'
25*4882a593Smuzhiyun        self.machine =  'qemux86-64'
26*4882a593Smuzhiyun        self.fstypes = "ext4 iso hddimg wic.vmdk wic.qcow2 wic.vdi"
27*4882a593Smuzhiyun        self.cmd_common = "runqemu nographic"
28*4882a593Smuzhiyun
29*4882a593Smuzhiyun        kvm = oe.types.qemu_use_kvm(get_bb_var('QEMU_USE_KVM'), 'x86_64')
30*4882a593Smuzhiyun        if kvm:
31*4882a593Smuzhiyun            self.cmd_common += " kvm"
32*4882a593Smuzhiyun
33*4882a593Smuzhiyun        self.write_config(
34*4882a593Smuzhiyun"""
35*4882a593SmuzhiyunMACHINE = "%s"
36*4882a593SmuzhiyunIMAGE_FSTYPES = "%s"
37*4882a593Smuzhiyun# 10 means 1 second
38*4882a593SmuzhiyunSYSLINUX_TIMEOUT = "10"
39*4882a593Smuzhiyun"""
40*4882a593Smuzhiyun% (self.machine, self.fstypes)
41*4882a593Smuzhiyun        )
42*4882a593Smuzhiyun
43*4882a593Smuzhiyun        if not RunqemuTests.image_is_ready:
44*4882a593Smuzhiyun            RunqemuTests.deploy_dir_image = get_bb_var('DEPLOY_DIR_IMAGE')
45*4882a593Smuzhiyun            bitbake(self.recipe)
46*4882a593Smuzhiyun            RunqemuTests.image_is_ready = True
47*4882a593Smuzhiyun
48*4882a593Smuzhiyun    def test_boot_machine(self):
49*4882a593Smuzhiyun        """Test runqemu machine"""
50*4882a593Smuzhiyun        cmd = "%s %s" % (self.cmd_common, self.machine)
51*4882a593Smuzhiyun        with runqemu(self.recipe, ssh=False, launch_cmd=cmd) as qemu:
52*4882a593Smuzhiyun            with open(qemu.qemurunnerlog) as f:
53*4882a593Smuzhiyun                self.assertTrue(qemu.runner.logged, "Failed: %s, %s" % (cmd, f.read()))
54*4882a593Smuzhiyun
55*4882a593Smuzhiyun    def test_boot_machine_ext4(self):
56*4882a593Smuzhiyun        """Test runqemu machine ext4"""
57*4882a593Smuzhiyun        cmd = "%s %s ext4" % (self.cmd_common, self.machine)
58*4882a593Smuzhiyun        with runqemu(self.recipe, ssh=False, launch_cmd=cmd) as qemu:
59*4882a593Smuzhiyun            with open(qemu.qemurunnerlog) as f:
60*4882a593Smuzhiyun                self.assertIn('rootfs.ext4', f.read(), "Failed: %s" % cmd)
61*4882a593Smuzhiyun
62*4882a593Smuzhiyun    def test_boot_machine_iso(self):
63*4882a593Smuzhiyun        """Test runqemu machine iso"""
64*4882a593Smuzhiyun        cmd = "%s %s iso" % (self.cmd_common, self.machine)
65*4882a593Smuzhiyun        with runqemu(self.recipe, ssh=False, launch_cmd=cmd) as qemu:
66*4882a593Smuzhiyun            with open(qemu.qemurunnerlog) as f:
67*4882a593Smuzhiyun                self.assertIn('media=cdrom', f.read(), "Failed: %s" % cmd)
68*4882a593Smuzhiyun
69*4882a593Smuzhiyun    def test_boot_recipe_image(self):
70*4882a593Smuzhiyun        """Test runqemu recipe-image"""
71*4882a593Smuzhiyun        cmd = "%s %s" % (self.cmd_common, self.recipe)
72*4882a593Smuzhiyun        with runqemu(self.recipe, ssh=False, launch_cmd=cmd) as qemu:
73*4882a593Smuzhiyun            with open(qemu.qemurunnerlog) as f:
74*4882a593Smuzhiyun                self.assertTrue(qemu.runner.logged, "Failed: %s, %s" % (cmd, f.read()))
75*4882a593Smuzhiyun
76*4882a593Smuzhiyun
77*4882a593Smuzhiyun    def test_boot_recipe_image_vmdk(self):
78*4882a593Smuzhiyun        """Test runqemu recipe-image vmdk"""
79*4882a593Smuzhiyun        cmd = "%s %s wic.vmdk" % (self.cmd_common, self.recipe)
80*4882a593Smuzhiyun        with runqemu(self.recipe, ssh=False, launch_cmd=cmd) as qemu:
81*4882a593Smuzhiyun            with open(qemu.qemurunnerlog) as f:
82*4882a593Smuzhiyun                self.assertIn('format=vmdk', f.read(), "Failed: %s" % cmd)
83*4882a593Smuzhiyun
84*4882a593Smuzhiyun    def test_boot_recipe_image_vdi(self):
85*4882a593Smuzhiyun        """Test runqemu recipe-image vdi"""
86*4882a593Smuzhiyun        cmd = "%s %s wic.vdi" % (self.cmd_common, self.recipe)
87*4882a593Smuzhiyun        with runqemu(self.recipe, ssh=False, launch_cmd=cmd) as qemu:
88*4882a593Smuzhiyun            with open(qemu.qemurunnerlog) as f:
89*4882a593Smuzhiyun                self.assertIn('format=vdi', f.read(), "Failed: %s" % cmd)
90*4882a593Smuzhiyun
91*4882a593Smuzhiyun    def test_boot_deploy(self):
92*4882a593Smuzhiyun        """Test runqemu deploy_dir_image"""
93*4882a593Smuzhiyun        cmd = "%s %s" % (self.cmd_common, self.deploy_dir_image)
94*4882a593Smuzhiyun        with runqemu(self.recipe, ssh=False, launch_cmd=cmd) as qemu:
95*4882a593Smuzhiyun            with open(qemu.qemurunnerlog) as f:
96*4882a593Smuzhiyun                self.assertTrue(qemu.runner.logged, "Failed: %s, %s" % (cmd, f.read()))
97*4882a593Smuzhiyun
98*4882a593Smuzhiyun
99*4882a593Smuzhiyun    def test_boot_deploy_hddimg(self):
100*4882a593Smuzhiyun        """Test runqemu deploy_dir_image hddimg"""
101*4882a593Smuzhiyun        cmd = "%s %s hddimg" % (self.cmd_common, self.deploy_dir_image)
102*4882a593Smuzhiyun        with runqemu(self.recipe, ssh=False, launch_cmd=cmd) as qemu:
103*4882a593Smuzhiyun            with open(qemu.qemurunnerlog) as f:
104*4882a593Smuzhiyun                self.assertTrue(re.search('file=.*.hddimg', f.read()), "Failed: %s, %s" % (cmd, f.read()))
105*4882a593Smuzhiyun
106*4882a593Smuzhiyun    def test_boot_machine_slirp(self):
107*4882a593Smuzhiyun        """Test runqemu machine slirp"""
108*4882a593Smuzhiyun        cmd = "%s slirp %s" % (self.cmd_common, self.machine)
109*4882a593Smuzhiyun        with runqemu(self.recipe, ssh=False, launch_cmd=cmd) as qemu:
110*4882a593Smuzhiyun            with open(qemu.qemurunnerlog) as f:
111*4882a593Smuzhiyun                self.assertIn(' -netdev user', f.read(), "Failed: %s" % cmd)
112*4882a593Smuzhiyun
113*4882a593Smuzhiyun    def test_boot_machine_slirp_qcow2(self):
114*4882a593Smuzhiyun        """Test runqemu machine slirp qcow2"""
115*4882a593Smuzhiyun        cmd = "%s slirp wic.qcow2 %s" % (self.cmd_common, self.machine)
116*4882a593Smuzhiyun        with runqemu(self.recipe, ssh=False, launch_cmd=cmd) as qemu:
117*4882a593Smuzhiyun            with open(qemu.qemurunnerlog) as f:
118*4882a593Smuzhiyun                self.assertIn('format=qcow2', f.read(), "Failed: %s" % cmd)
119*4882a593Smuzhiyun
120*4882a593Smuzhiyun    def test_boot_qemu_boot(self):
121*4882a593Smuzhiyun        """Test runqemu /path/to/image.qemuboot.conf"""
122*4882a593Smuzhiyun        qemuboot_conf = "%s-%s.qemuboot.conf" % (self.recipe, self.machine)
123*4882a593Smuzhiyun        qemuboot_conf = os.path.join(self.deploy_dir_image, qemuboot_conf)
124*4882a593Smuzhiyun        if not os.path.exists(qemuboot_conf):
125*4882a593Smuzhiyun            self.skipTest("%s not found" % qemuboot_conf)
126*4882a593Smuzhiyun        cmd = "%s %s" % (self.cmd_common, qemuboot_conf)
127*4882a593Smuzhiyun        with runqemu(self.recipe, ssh=False, launch_cmd=cmd) as qemu:
128*4882a593Smuzhiyun            with open(qemu.qemurunnerlog) as f:
129*4882a593Smuzhiyun                self.assertTrue(qemu.runner.logged, "Failed: %s, %s" % (cmd, f.read()))
130*4882a593Smuzhiyun
131*4882a593Smuzhiyun    def test_boot_rootfs(self):
132*4882a593Smuzhiyun        """Test runqemu /path/to/rootfs.ext4"""
133*4882a593Smuzhiyun        rootfs = "%s-%s.ext4" % (self.recipe, self.machine)
134*4882a593Smuzhiyun        rootfs = os.path.join(self.deploy_dir_image, rootfs)
135*4882a593Smuzhiyun        if not os.path.exists(rootfs):
136*4882a593Smuzhiyun            self.skipTest("%s not found" % rootfs)
137*4882a593Smuzhiyun        cmd = "%s %s" % (self.cmd_common, rootfs)
138*4882a593Smuzhiyun        with runqemu(self.recipe, ssh=False, launch_cmd=cmd) as qemu:
139*4882a593Smuzhiyun            with open(qemu.qemurunnerlog) as f:
140*4882a593Smuzhiyun                self.assertTrue(qemu.runner.logged, "Failed: %s, %s" % (cmd, f.read()))
141*4882a593Smuzhiyun
142*4882a593Smuzhiyun
143*4882a593Smuzhiyun# This test was designed as a separate class to test that shutdown
144*4882a593Smuzhiyun# command will shutdown qemu as expected on each qemu architecture
145*4882a593Smuzhiyun# based on the MACHINE configuration inside the config file
146*4882a593Smuzhiyun# (eg. local.conf).
147*4882a593Smuzhiyun#
148*4882a593Smuzhiyun# This was different compared to RunqemuTests, where RunqemuTests was
149*4882a593Smuzhiyun# dedicated for MACHINE=qemux86-64 where it test that qemux86-64 will
150*4882a593Smuzhiyun# bootup various filesystem types, including live image(iso and hddimg)
151*4882a593Smuzhiyun# where live image was not supported on all qemu architecture.
152*4882a593Smuzhiyun@OETestTag("machine")
153*4882a593Smuzhiyun@OETestTag("runqemu")
154*4882a593Smuzhiyunclass QemuTest(OESelftestTestCase):
155*4882a593Smuzhiyun
156*4882a593Smuzhiyun    @classmethod
157*4882a593Smuzhiyun    def setUpClass(cls):
158*4882a593Smuzhiyun        super(QemuTest, cls).setUpClass()
159*4882a593Smuzhiyun        cls.recipe = 'core-image-minimal'
160*4882a593Smuzhiyun        cls.machine =  get_bb_var('MACHINE')
161*4882a593Smuzhiyun        cls.deploy_dir_image =  get_bb_var('DEPLOY_DIR_IMAGE')
162*4882a593Smuzhiyun        cls.cmd_common = "runqemu nographic"
163*4882a593Smuzhiyun        cls.qemuboot_conf = "%s-%s.qemuboot.conf" % (cls.recipe, cls.machine)
164*4882a593Smuzhiyun        cls.qemuboot_conf = os.path.join(cls.deploy_dir_image, cls.qemuboot_conf)
165*4882a593Smuzhiyun        bitbake(cls.recipe)
166*4882a593Smuzhiyun
167*4882a593Smuzhiyun    def _start_qemu_shutdown_check_if_shutdown_succeeded(self, qemu, timeout):
168*4882a593Smuzhiyun        # Allow the runner's LoggingThread instance to exit without errors
169*4882a593Smuzhiyun        # (such as the exception "Console connection closed unexpectedly")
170*4882a593Smuzhiyun        # as qemu will disappear when we shut it down
171*4882a593Smuzhiyun        qemu.runner.allowexit()
172*4882a593Smuzhiyun        qemu.run_serial("shutdown -h now")
173*4882a593Smuzhiyun        time_track = 0
174*4882a593Smuzhiyun        try:
175*4882a593Smuzhiyun            while True:
176*4882a593Smuzhiyun                is_alive = qemu.check()
177*4882a593Smuzhiyun                if not is_alive:
178*4882a593Smuzhiyun                    return True
179*4882a593Smuzhiyun                if time_track > timeout:
180*4882a593Smuzhiyun                    return False
181*4882a593Smuzhiyun                time.sleep(1)
182*4882a593Smuzhiyun                time_track += 1
183*4882a593Smuzhiyun        except SystemExit:
184*4882a593Smuzhiyun            return True
185*4882a593Smuzhiyun
186*4882a593Smuzhiyun    def test_qemu_can_shutdown(self):
187*4882a593Smuzhiyun        self.assertExists(self.qemuboot_conf)
188*4882a593Smuzhiyun        cmd = "%s %s" % (self.cmd_common, self.qemuboot_conf)
189*4882a593Smuzhiyun        shutdown_timeout = 120
190*4882a593Smuzhiyun        with runqemu(self.recipe, ssh=False, launch_cmd=cmd) as qemu:
191*4882a593Smuzhiyun            qemu_shutdown_succeeded = self._start_qemu_shutdown_check_if_shutdown_succeeded(qemu, shutdown_timeout)
192*4882a593Smuzhiyun            self.assertTrue(qemu_shutdown_succeeded, 'Failed: %s does not shutdown within timeout(%s)' % (self.machine, shutdown_timeout))
193*4882a593Smuzhiyun
194*4882a593Smuzhiyun    # Need to have portmap/rpcbind running to allow this test to work and
195*4882a593Smuzhiyun    # current autobuilder setup does not have this.
196*4882a593Smuzhiyun    def disabled_test_qemu_can_boot_nfs_and_shutdown(self):
197*4882a593Smuzhiyun        self.assertExists(self.qemuboot_conf)
198*4882a593Smuzhiyun        bitbake('meta-ide-support')
199*4882a593Smuzhiyun        rootfs_tar = "%s-%s.tar.bz2" % (self.recipe, self.machine)
200*4882a593Smuzhiyun        rootfs_tar = os.path.join(self.deploy_dir_image, rootfs_tar)
201*4882a593Smuzhiyun        self.assertExists(rootfs_tar)
202*4882a593Smuzhiyun        tmpdir = tempfile.mkdtemp(prefix='qemu_nfs')
203*4882a593Smuzhiyun        tmpdir_nfs = os.path.join(tmpdir, 'nfs')
204*4882a593Smuzhiyun        cmd_extract_nfs = 'runqemu-extract-sdk %s %s' % (rootfs_tar, tmpdir_nfs)
205*4882a593Smuzhiyun        result = runCmd(cmd_extract_nfs)
206*4882a593Smuzhiyun        self.assertEqual(0, result.status, "runqemu-extract-sdk didn't run as expected. %s" % result.output)
207*4882a593Smuzhiyun        cmd = "%s nfs %s %s" % (self.cmd_common, self.qemuboot_conf, tmpdir_nfs)
208*4882a593Smuzhiyun        shutdown_timeout = 120
209*4882a593Smuzhiyun        with runqemu(self.recipe, ssh=False, launch_cmd=cmd) as qemu:
210*4882a593Smuzhiyun            qemu_shutdown_succeeded = self._start_qemu_shutdown_check_if_shutdown_succeeded(qemu, shutdown_timeout)
211*4882a593Smuzhiyun            self.assertTrue(qemu_shutdown_succeeded, 'Failed: %s does not shutdown within timeout(%s)' % (self.machine, shutdown_timeout))
212*4882a593Smuzhiyun        runCmd('rm -rf %s' % tmpdir)
213