1*fcf2658bSPhilippe Mathieu-Daudé#!/usr/bin/env python3 2*fcf2658bSPhilippe Mathieu-Daudé# 3*fcf2658bSPhilippe Mathieu-Daudé# Functional tests for the little-endian 64-bit MIPS Malta board 4*fcf2658bSPhilippe Mathieu-Daudé# 5*fcf2658bSPhilippe Mathieu-Daudé# Copyright (c) Philippe Mathieu-Daudé <f4bug@amsat.org> 6*fcf2658bSPhilippe Mathieu-Daudé# 7*fcf2658bSPhilippe Mathieu-Daudé# This work is licensed under the terms of the GNU GPL, version 2 or later. 8*fcf2658bSPhilippe Mathieu-Daudé# See the COPYING file in the top-level directory. 9*fcf2658bSPhilippe Mathieu-Daudé# 10*fcf2658bSPhilippe Mathieu-Daudé# SPDX-License-Identifier: GPL-2.0-or-later 11*fcf2658bSPhilippe Mathieu-Daudé 12*fcf2658bSPhilippe Mathieu-Daudéimport os 13*fcf2658bSPhilippe Mathieu-Daudéimport logging 14*fcf2658bSPhilippe Mathieu-Daudé 15*fcf2658bSPhilippe Mathieu-Daudéfrom qemu_test import LinuxKernelTest, Asset 16*fcf2658bSPhilippe Mathieu-Daudéfrom qemu_test import exec_command_and_wait_for_pattern 17*fcf2658bSPhilippe Mathieu-Daudéfrom qemu_test.utils import gzip_uncompress 18*fcf2658bSPhilippe Mathieu-Daudéfrom unittest import skipUnless 19*fcf2658bSPhilippe Mathieu-Daudé 20*fcf2658bSPhilippe Mathieu-DaudéNUMPY_AVAILABLE = True 21*fcf2658bSPhilippe Mathieu-Daudétry: 22*fcf2658bSPhilippe Mathieu-Daudé import numpy as np 23*fcf2658bSPhilippe Mathieu-Daudéexcept ImportError: 24*fcf2658bSPhilippe Mathieu-Daudé NUMPY_AVAILABLE = False 25*fcf2658bSPhilippe Mathieu-Daudé 26*fcf2658bSPhilippe Mathieu-DaudéCV2_AVAILABLE = True 27*fcf2658bSPhilippe Mathieu-Daudétry: 28*fcf2658bSPhilippe Mathieu-Daudé import cv2 29*fcf2658bSPhilippe Mathieu-Daudéexcept ImportError: 30*fcf2658bSPhilippe Mathieu-Daudé CV2_AVAILABLE = False 31*fcf2658bSPhilippe Mathieu-Daudé 32*fcf2658bSPhilippe Mathieu-Daudé 33*fcf2658bSPhilippe Mathieu-Daudé@skipUnless(NUMPY_AVAILABLE, 'Python NumPy not installed') 34*fcf2658bSPhilippe Mathieu-Daudé@skipUnless(CV2_AVAILABLE, 'Python OpenCV not installed') 35*fcf2658bSPhilippe Mathieu-Daudéclass MaltaMachineFramebuffer(LinuxKernelTest): 36*fcf2658bSPhilippe Mathieu-Daudé 37*fcf2658bSPhilippe Mathieu-Daudé timeout = 30 38*fcf2658bSPhilippe Mathieu-Daudé 39*fcf2658bSPhilippe Mathieu-Daudé ASSET_KERNEL_4_7_0 = Asset( 40*fcf2658bSPhilippe Mathieu-Daudé ('https://github.com/philmd/qemu-testing-blob/raw/a5966ca4b5/' 41*fcf2658bSPhilippe Mathieu-Daudé 'mips/malta/mips64el/vmlinux-4.7.0-rc1.I6400.gz'), 42*fcf2658bSPhilippe Mathieu-Daudé '1f64efc59968a3c328672e6b10213fe574bb2308d9d2ed44e75e40be59e9fbc2') 43*fcf2658bSPhilippe Mathieu-Daudé 44*fcf2658bSPhilippe Mathieu-Daudé ASSET_TUXLOGO = Asset( 45*fcf2658bSPhilippe Mathieu-Daudé ('https://github.com/torvalds/linux/raw/v2.6.12/' 46*fcf2658bSPhilippe Mathieu-Daudé 'drivers/video/logo/logo_linux_vga16.ppm'), 47*fcf2658bSPhilippe Mathieu-Daudé 'b762f0d91ec018887ad1b334543c2fdf9be9fdfc87672b409211efaa3ea0ef79') 48*fcf2658bSPhilippe Mathieu-Daudé 49*fcf2658bSPhilippe Mathieu-Daudé def do_test_i6400_framebuffer_logo(self, cpu_cores_count): 50*fcf2658bSPhilippe Mathieu-Daudé """ 51*fcf2658bSPhilippe Mathieu-Daudé Boot Linux kernel and check Tux logo is displayed on the framebuffer. 52*fcf2658bSPhilippe Mathieu-Daudé """ 53*fcf2658bSPhilippe Mathieu-Daudé screendump_path = os.path.join(self.workdir, 'screendump.pbm') 54*fcf2658bSPhilippe Mathieu-Daudé 55*fcf2658bSPhilippe Mathieu-Daudé kernel_path_gz = self.ASSET_KERNEL_4_7_0.fetch() 56*fcf2658bSPhilippe Mathieu-Daudé kernel_path = self.workdir + "vmlinux" 57*fcf2658bSPhilippe Mathieu-Daudé gzip_uncompress(kernel_path_gz, kernel_path) 58*fcf2658bSPhilippe Mathieu-Daudé 59*fcf2658bSPhilippe Mathieu-Daudé tuxlogo_path = self.ASSET_TUXLOGO.fetch() 60*fcf2658bSPhilippe Mathieu-Daudé 61*fcf2658bSPhilippe Mathieu-Daudé self.set_machine('malta') 62*fcf2658bSPhilippe Mathieu-Daudé self.vm.set_console() 63*fcf2658bSPhilippe Mathieu-Daudé kernel_command_line = (self.KERNEL_COMMON_COMMAND_LINE + 64*fcf2658bSPhilippe Mathieu-Daudé 'clocksource=GIC console=tty0 console=ttyS0') 65*fcf2658bSPhilippe Mathieu-Daudé self.vm.add_args('-kernel', kernel_path, 66*fcf2658bSPhilippe Mathieu-Daudé '-cpu', 'I6400', 67*fcf2658bSPhilippe Mathieu-Daudé '-smp', '%u' % cpu_cores_count, 68*fcf2658bSPhilippe Mathieu-Daudé '-vga', 'std', 69*fcf2658bSPhilippe Mathieu-Daudé '-append', kernel_command_line) 70*fcf2658bSPhilippe Mathieu-Daudé self.vm.launch() 71*fcf2658bSPhilippe Mathieu-Daudé framebuffer_ready = 'Console: switching to colour frame buffer device' 72*fcf2658bSPhilippe Mathieu-Daudé self.wait_for_console_pattern(framebuffer_ready) 73*fcf2658bSPhilippe Mathieu-Daudé self.vm.cmd('human-monitor-command', command_line='stop') 74*fcf2658bSPhilippe Mathieu-Daudé self.vm.cmd('human-monitor-command', 75*fcf2658bSPhilippe Mathieu-Daudé command_line='screendump %s' % screendump_path) 76*fcf2658bSPhilippe Mathieu-Daudé logger = logging.getLogger('framebuffer') 77*fcf2658bSPhilippe Mathieu-Daudé 78*fcf2658bSPhilippe Mathieu-Daudé match_threshold = 0.95 79*fcf2658bSPhilippe Mathieu-Daudé screendump_bgr = cv2.imread(screendump_path, cv2.IMREAD_COLOR) 80*fcf2658bSPhilippe Mathieu-Daudé tuxlogo_bgr = cv2.imread(tuxlogo_path, cv2.IMREAD_COLOR) 81*fcf2658bSPhilippe Mathieu-Daudé result = cv2.matchTemplate(screendump_bgr, tuxlogo_bgr, 82*fcf2658bSPhilippe Mathieu-Daudé cv2.TM_CCOEFF_NORMED) 83*fcf2658bSPhilippe Mathieu-Daudé loc = np.where(result >= match_threshold) 84*fcf2658bSPhilippe Mathieu-Daudé tuxlogo_count = 0 85*fcf2658bSPhilippe Mathieu-Daudé h, w = tuxlogo_bgr.shape[:2] 86*fcf2658bSPhilippe Mathieu-Daudé debug_png = os.getenv('AVOCADO_CV2_SCREENDUMP_PNG_PATH') 87*fcf2658bSPhilippe Mathieu-Daudé for tuxlogo_count, pt in enumerate(zip(*loc[::-1]), start=1): 88*fcf2658bSPhilippe Mathieu-Daudé logger.debug('found Tux at position (x, y) = %s', pt) 89*fcf2658bSPhilippe Mathieu-Daudé cv2.rectangle(screendump_bgr, pt, 90*fcf2658bSPhilippe Mathieu-Daudé (pt[0] + w, pt[1] + h), (0, 0, 255), 2) 91*fcf2658bSPhilippe Mathieu-Daudé if debug_png: 92*fcf2658bSPhilippe Mathieu-Daudé cv2.imwrite(debug_png, screendump_bgr) 93*fcf2658bSPhilippe Mathieu-Daudé self.assertGreaterEqual(tuxlogo_count, cpu_cores_count) 94*fcf2658bSPhilippe Mathieu-Daudé 95*fcf2658bSPhilippe Mathieu-Daudé def test_mips_malta_i6400_framebuffer_logo_1core(self): 96*fcf2658bSPhilippe Mathieu-Daudé self.do_test_i6400_framebuffer_logo(1) 97*fcf2658bSPhilippe Mathieu-Daudé 98*fcf2658bSPhilippe Mathieu-Daudé @skipUnless(os.getenv('QEMU_TEST_FLAKY_TESTS'), 'Test is unstable on GitLab') 99*fcf2658bSPhilippe Mathieu-Daudé def test_mips_malta_i6400_framebuffer_logo_7cores(self): 100*fcf2658bSPhilippe Mathieu-Daudé self.do_test_i6400_framebuffer_logo(7) 101*fcf2658bSPhilippe Mathieu-Daudé 102*fcf2658bSPhilippe Mathieu-Daudé @skipUnless(os.getenv('QEMU_TEST_FLAKY_TESTS'), 'Test is unstable on GitLab') 103*fcf2658bSPhilippe Mathieu-Daudé def test_mips_malta_i6400_framebuffer_logo_8cores(self): 104*fcf2658bSPhilippe Mathieu-Daudé self.do_test_i6400_framebuffer_logo(8) 105*fcf2658bSPhilippe Mathieu-Daudé 106*fcf2658bSPhilippe Mathieu-Daudé 107*fcf2658bSPhilippe Mathieu-Daudéif __name__ == '__main__': 108*fcf2658bSPhilippe Mathieu-Daudé LinuxKernelTest.main() 109