xref: /aosp_15_r20/external/igt-gpu-tools/scripts/test_igt_gpu_tools.py (revision d83cc019efdc2edc6c4b16e9034a3ceb8d35d77c)
1*d83cc019SAndroid Build Coastguard Worker#!/usr/bin/env python3
2*d83cc019SAndroid Build Coastguard Worker
3*d83cc019SAndroid Build Coastguard Worker# Copyright (C) 2020 The Android Open Source Project
4*d83cc019SAndroid Build Coastguard Worker
5*d83cc019SAndroid Build Coastguard Worker# Licensed under the Apache License, Version 2.0 (the "License");
6*d83cc019SAndroid Build Coastguard Worker# you may not use this file except in compliance with the License.
7*d83cc019SAndroid Build Coastguard Worker# You may obtain a copy of the License at
8*d83cc019SAndroid Build Coastguard Worker#
9*d83cc019SAndroid Build Coastguard Worker#      http://www.apache.org/licenses/LICENSE-2.0
10*d83cc019SAndroid Build Coastguard Worker#
11*d83cc019SAndroid Build Coastguard Worker# Unless required by applicable law or agreed to in writing, software
12*d83cc019SAndroid Build Coastguard Worker# distributed under the License is distributed on an "AS IS" BASIS,
13*d83cc019SAndroid Build Coastguard Worker# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14*d83cc019SAndroid Build Coastguard Worker# See the License for the specific language governing permissions and
15*d83cc019SAndroid Build Coastguard Worker# limitations under the License.
16*d83cc019SAndroid Build Coastguard Worker
17*d83cc019SAndroid Build Coastguard Workerimport os
18*d83cc019SAndroid Build Coastguard Workerimport unittest
19*d83cc019SAndroid Build Coastguard Workerfrom xml.etree import ElementTree
20*d83cc019SAndroid Build Coastguard Workerimport subprocess
21*d83cc019SAndroid Build Coastguard Workerimport sys
22*d83cc019SAndroid Build Coastguard Worker
23*d83cc019SAndroid Build Coastguard WorkerVERBOSE = True
24*d83cc019SAndroid Build Coastguard WorkerTEST_CONFIG = os.path.join(os.path.dirname(__file__), "test_igt_gpu_tools.xml")
25*d83cc019SAndroid Build Coastguard Worker
26*d83cc019SAndroid Build Coastguard Worker""" Extracts tests from AndroidTest.xml compatible file
27*d83cc019SAndroid Build Coastguard Worker    param: xmlfile str containing path to AndroidTest.xml compatible xml file
28*d83cc019SAndroid Build Coastguard Worker"""
29*d83cc019SAndroid Build Coastguard Workerdef extract_tests_from_xml(xmlfile):
30*d83cc019SAndroid Build Coastguard Worker    tree = ElementTree.parse(xmlfile)
31*d83cc019SAndroid Build Coastguard Worker    root = tree.getroot()
32*d83cc019SAndroid Build Coastguard Worker    return [(o.attrib['key'], o.attrib['value'])
33*d83cc019SAndroid Build Coastguard Worker            for o in root.findall("./target_preparer/option")
34*d83cc019SAndroid Build Coastguard Worker            if o.attrib['name'] == "push-file"]
35*d83cc019SAndroid Build Coastguard Worker
36*d83cc019SAndroid Build Coastguard Workerdef run_command(command):
37*d83cc019SAndroid Build Coastguard Worker    serial_number = os.environ.get("ANDROID_SERIAL", "")
38*d83cc019SAndroid Build Coastguard Worker    if not serial_number:
39*d83cc019SAndroid Build Coastguard Worker        raise "$ANDROID_SERIAL is empty, device must be specified"
40*d83cc019SAndroid Build Coastguard Worker    full_command = ["adb", "-s", serial_number, "shell"] + command
41*d83cc019SAndroid Build Coastguard Worker    if VERBOSE:
42*d83cc019SAndroid Build Coastguard Worker        print("+" + " ".join(full_command))
43*d83cc019SAndroid Build Coastguard Worker    ret = subprocess.run(full_command, capture_output=True, universal_newlines=True)
44*d83cc019SAndroid Build Coastguard Worker    if VERBOSE:
45*d83cc019SAndroid Build Coastguard Worker        print(ret.stdout)
46*d83cc019SAndroid Build Coastguard Worker    return ret.stdout
47*d83cc019SAndroid Build Coastguard Worker
48*d83cc019SAndroid Build Coastguard Workerclass IGTGpuToolsBinary():
49*d83cc019SAndroid Build Coastguard Worker    """Harness object for a specific IGT GPU test binary. """
50*d83cc019SAndroid Build Coastguard Worker
51*d83cc019SAndroid Build Coastguard Worker    """ param: ondevice_test_path The IGT binary path on device """
52*d83cc019SAndroid Build Coastguard Worker    def __init__(self, ondevice_test_path):
53*d83cc019SAndroid Build Coastguard Worker        self._path = ondevice_test_path
54*d83cc019SAndroid Build Coastguard Worker        subtests = run_command([self._path, "--list-subtests"])
55*d83cc019SAndroid Build Coastguard Worker        self._subtests = list(filter(lambda x: x != "", subtests.split("\n")))
56*d83cc019SAndroid Build Coastguard Worker
57*d83cc019SAndroid Build Coastguard Worker    """lists subtests detected in tests.
58*d83cc019SAndroid Build Coastguard Worker       return: list of strings indicating subtests found in binary.
59*d83cc019SAndroid Build Coastguard Worker    """
60*d83cc019SAndroid Build Coastguard Worker    def subtests(self):
61*d83cc019SAndroid Build Coastguard Worker        return self._subtests;
62*d83cc019SAndroid Build Coastguard Worker
63*d83cc019SAndroid Build Coastguard Worker    """Runs a subtest.
64*d83cc019SAndroid Build Coastguard Worker
65*d83cc019SAndroid Build Coastguard Worker        param: subtest_name One of the subtests listed by self.subtest()
66*d83cc019SAndroid Build Coastguard Worker        return: a subprocess.CompletedProcess
67*d83cc019SAndroid Build Coastguard Worker    """
68*d83cc019SAndroid Build Coastguard Worker    def run_subtest(self, subtest_name):
69*d83cc019SAndroid Build Coastguard Worker        if subtest_name not in self._subtests:
70*d83cc019SAndroid Build Coastguard Worker            error
71*d83cc019SAndroid Build Coastguard Worker        return run_command([self._path, "--run-subtest", subtest_name])
72*d83cc019SAndroid Build Coastguard Worker
73*d83cc019SAndroid Build Coastguard Workerclass IGTGpuToolsTest(unittest.TestCase):
74*d83cc019SAndroid Build Coastguard Worker    """Tests for DRM/KMS using Intel Graphics Tests suite"""
75*d83cc019SAndroid Build Coastguard Worker
76*d83cc019SAndroid Build Coastguard Worker    """ param: subtest A valid subtest for the binary
77*d83cc019SAndroid Build Coastguard Worker        param: the IGT binary to run as a unit test.
78*d83cc019SAndroid Build Coastguard Worker    """
79*d83cc019SAndroid Build Coastguard Worker    def __init__(self, subtest, binary):
80*d83cc019SAndroid Build Coastguard Worker        self._subtest_name = subtest
81*d83cc019SAndroid Build Coastguard Worker        self._test_binary = binary
82*d83cc019SAndroid Build Coastguard Worker        setattr(self, self._subtest_name, self.runTest)
83*d83cc019SAndroid Build Coastguard Worker        super(IGTGpuToolsTest, self).__init__(methodName=self._subtest_name)
84*d83cc019SAndroid Build Coastguard Worker
85*d83cc019SAndroid Build Coastguard Worker    """ Runs the test set in the constructor """
86*d83cc019SAndroid Build Coastguard Worker    def runTest(self):
87*d83cc019SAndroid Build Coastguard Worker        output = self._test_binary.run_subtest(self._subtest_name)
88*d83cc019SAndroid Build Coastguard Worker        for line in output.split("\n"):
89*d83cc019SAndroid Build Coastguard Worker            if "Subtest" not in line:
90*d83cc019SAndroid Build Coastguard Worker                continue;
91*d83cc019SAndroid Build Coastguard Worker            if "SKIP" in line:
92*d83cc019SAndroid Build Coastguard Worker                self.skipTest("{} - skipped".format(self._subtest_name))
93*d83cc019SAndroid Build Coastguard Worker                break
94*d83cc019SAndroid Build Coastguard Worker            if "SUCCESS" in line:
95*d83cc019SAndroid Build Coastguard Worker                break
96*d83cc019SAndroid Build Coastguard Worker            if "FAIL" in line:
97*d83cc019SAndroid Build Coastguard Worker                self.fail(output)
98*d83cc019SAndroid Build Coastguard Worker                break
99*d83cc019SAndroid Build Coastguard Worker            self.fail("could not parse test output; test runner failure")
100*d83cc019SAndroid Build Coastguard Worker
101*d83cc019SAndroid Build Coastguard WorkerANDROID_RUNNER_REQUIRED_VERBOSITY = 2
102*d83cc019SAndroid Build Coastguard Worker
103*d83cc019SAndroid Build Coastguard Workerdef main():
104*d83cc019SAndroid Build Coastguard Worker    """main entrypoint for test runner"""
105*d83cc019SAndroid Build Coastguard Worker
106*d83cc019SAndroid Build Coastguard Worker    runner = unittest.TextTestRunner(stream=sys.stderr, verbosity=ANDROID_RUNNER_REQUIRED_VERBOSITY)
107*d83cc019SAndroid Build Coastguard Worker    suite = unittest.TestSuite()
108*d83cc019SAndroid Build Coastguard Worker    for test, test_path in extract_tests_from_xml(TEST_CONFIG):
109*d83cc019SAndroid Build Coastguard Worker        print("Found IGT-GPU-tools test {}".format(test))
110*d83cc019SAndroid Build Coastguard Worker        subsuite = unittest.TestSuite()
111*d83cc019SAndroid Build Coastguard Worker        binary = IGTGpuToolsBinary(test_path)
112*d83cc019SAndroid Build Coastguard Worker        for subtest in binary.subtests():
113*d83cc019SAndroid Build Coastguard Worker            print("\tFound subtest {}".format(subtest))
114*d83cc019SAndroid Build Coastguard Worker            subsuite.addTest(IGTGpuToolsTest(subtest, binary))
115*d83cc019SAndroid Build Coastguard Worker        suite.addTest(subsuite)
116*d83cc019SAndroid Build Coastguard Worker    runner.run(suite)
117*d83cc019SAndroid Build Coastguard Worker
118*d83cc019SAndroid Build Coastguard Workerif __name__=="__main__":
119*d83cc019SAndroid Build Coastguard Worker    main()
120