xref: /qemu/tests/functional/acpi-bits/bits-tests/testacpi.py2 (revision 87853babb37759bcb144dd18925a340be8fe8244)
1*87853babSAni Sinha# Copyright (c) 2015, Intel Corporation
2*87853babSAni Sinha# All rights reserved.
3*87853babSAni Sinha#
4*87853babSAni Sinha# Redistribution and use in source and binary forms, with or without
5*87853babSAni Sinha# modification, are permitted provided that the following conditions are met:
6*87853babSAni Sinha#
7*87853babSAni Sinha#     * Redistributions of source code must retain the above copyright notice,
8*87853babSAni Sinha#       this list of conditions and the following disclaimer.
9*87853babSAni Sinha#     * Redistributions in binary form must reproduce the above copyright notice,
10*87853babSAni Sinha#       this list of conditions and the following disclaimer in the documentation
11*87853babSAni Sinha#       and/or other materials provided with the distribution.
12*87853babSAni Sinha#     * Neither the name of Intel Corporation nor the names of its contributors
13*87853babSAni Sinha#       may be used to endorse or promote products derived from this software
14*87853babSAni Sinha#       without specific prior written permission.
15*87853babSAni Sinha#
16*87853babSAni Sinha# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17*87853babSAni Sinha# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18*87853babSAni Sinha# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19*87853babSAni Sinha# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
20*87853babSAni Sinha# ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21*87853babSAni Sinha# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22*87853babSAni Sinha# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
23*87853babSAni Sinha# ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24*87853babSAni Sinha# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25*87853babSAni Sinha# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26*87853babSAni Sinha
27*87853babSAni Sinha"""Tests for ACPI"""
28*87853babSAni Sinha
29*87853babSAni Sinhaimport acpi
30*87853babSAni Sinhaimport bits
31*87853babSAni Sinhaimport bits.mwait
32*87853babSAni Sinhaimport struct
33*87853babSAni Sinhaimport testutil
34*87853babSAni Sinhaimport testsuite
35*87853babSAni Sinhaimport time
36*87853babSAni Sinha
37*87853babSAni Sinhadef register_tests():
38*87853babSAni Sinha    testsuite.add_test("ACPI _MAT (Multiple APIC Table Entry) under Processor objects", test_mat, submenu="ACPI Tests")
39*87853babSAni Sinha    testsuite.add_test("ACPI _PSS (Pstate) table conformance tests", test_pss, submenu="ACPI Tests")
40*87853babSAni Sinha    testsuite.add_test("ACPI _PSS (Pstate) runtime tests", test_pstates, submenu="ACPI Tests")
41*87853babSAni Sinha    testsuite.add_test("ACPI DSDT (Differentiated System Description Table)", test_dsdt, submenu="ACPI Tests")
42*87853babSAni Sinha    testsuite.add_test("ACPI FACP (Fixed ACPI Description Table)", test_facp, submenu="ACPI Tests")
43*87853babSAni Sinha    testsuite.add_test("ACPI HPET (High Precision Event Timer Table)", test_hpet, submenu="ACPI Tests")
44*87853babSAni Sinha    testsuite.add_test("ACPI MADT (Multiple APIC Description Table)", test_apic, submenu="ACPI Tests")
45*87853babSAni Sinha    testsuite.add_test("ACPI MPST (Memory Power State Table)", test_mpst, submenu="ACPI Tests")
46*87853babSAni Sinha    testsuite.add_test("ACPI RSDP (Root System Description Pointer Structure)", test_rsdp, submenu="ACPI Tests")
47*87853babSAni Sinha    testsuite.add_test("ACPI XSDT (Extended System Description Table)", test_xsdt, submenu="ACPI Tests")
48*87853babSAni Sinha
49*87853babSAni Sinhadef test_mat():
50*87853babSAni Sinha    cpupaths = acpi.get_cpupaths()
51*87853babSAni Sinha    apic = acpi.parse_apic()
52*87853babSAni Sinha    procid_apicid = apic.procid_apicid
53*87853babSAni Sinha    uid_x2apicid = apic.uid_x2apicid
54*87853babSAni Sinha    for cpupath in cpupaths:
55*87853babSAni Sinha        # Find the ProcId defined by the processor object
56*87853babSAni Sinha        processor = acpi.evaluate(cpupath)
57*87853babSAni Sinha        # Find the UID defined by the processor object's _UID method
58*87853babSAni Sinha        uid = acpi.evaluate(cpupath + "._UID")
59*87853babSAni Sinha        mat_buffer = acpi.evaluate(cpupath + "._MAT")
60*87853babSAni Sinha        if mat_buffer is None:
61*87853babSAni Sinha            continue
62*87853babSAni Sinha        # Process each _MAT subtable
63*87853babSAni Sinha        mat = acpi._MAT(mat_buffer)
64*87853babSAni Sinha        for index, subtable in enumerate(mat):
65*87853babSAni Sinha            if subtable.subtype == acpi.MADT_TYPE_LOCAL_APIC:
66*87853babSAni Sinha                if subtable.flags.bits.enabled:
67*87853babSAni Sinha                    testsuite.test("{} Processor declaration ProcId = _MAT ProcId".format(cpupath), processor.ProcId == subtable.proc_id)
68*87853babSAni Sinha                    testsuite.print_detail("{} ProcId ({:#02x}) != _MAT ProcId ({:#02x})".format(cpupath, processor.ProcId, subtable.proc_id))
69*87853babSAni Sinha                    testsuite.print_detail("Processor Declaration: {}".format(processor))
70*87853babSAni Sinha                    testsuite.print_detail("_MAT entry[{}]: {}".format(index, subtable))
71*87853babSAni Sinha                    if testsuite.test("{} with local APIC in _MAT has local APIC in MADT".format(cpupath), processor.ProcId in procid_apicid):
72*87853babSAni Sinha                        testsuite.test("{} ApicId derived using Processor declaration ProcId = _MAT ApicId".format(cpupath), procid_apicid[processor.ProcId] == subtable.apic_id)
73*87853babSAni Sinha                        testsuite.print_detail("{} ApicId derived from MADT ({:#02x}) != _MAT ApicId ({:#02x})".format(cpupath, procid_apicid[processor.ProcId], subtable.apic_id))
74*87853babSAni Sinha                        testsuite.print_detail("Processor Declaration: {}".format(processor))
75*87853babSAni Sinha                        testsuite.print_detail("_MAT entry[{}]: {}".format(index, subtable))
76*87853babSAni Sinha            if subtable.subtype == acpi.MADT_TYPE_LOCAL_X2APIC:
77*87853babSAni Sinha                if subtable.flags.bits.enabled:
78*87853babSAni Sinha                    if testsuite.test("{} with x2Apic in _MAT has _UID".format(cpupath), uid is not None):
79*87853babSAni Sinha                        testsuite.test("{}._UID = _MAT UID".format(cpupath), uid == subtable.uid)
80*87853babSAni Sinha                        testsuite.print_detail("{}._UID ({:#x}) != _MAT UID ({:#x})".format(cpupath, uid, subtable.uid))
81*87853babSAni Sinha                        testsuite.print_detail("_MAT entry[{}]: {}".format(index, subtable))
82*87853babSAni Sinha                    if testsuite.test("{} with _MAT x2Apic has x2Apic in MADT".format(cpupath), subtable.uid in uid_x2apicid):
83*87853babSAni Sinha                        testsuite.test("{} x2ApicId derived from MADT using UID = _MAT x2ApicId".format(cpupath), uid_x2apicid[subtable.uid] == subtable.x2apicid)
84*87853babSAni Sinha                        testsuite.print_detail("{} x2ApicId derived from MADT ({:#02x}) != _MAT x2ApicId ({:#02x})".format(cpupath, uid_x2apicid[subtable.uid], subtable.x2apicid))
85*87853babSAni Sinha                        testsuite.print_detail("_MAT entry[{}]: {}".format(index, subtable))
86*87853babSAni Sinha
87*87853babSAni Sinhadef test_pss():
88*87853babSAni Sinha    uniques = acpi.parse_cpu_method("_PSS")
89*87853babSAni Sinha    # We special-case None here to avoid a double-failure for CPUs without a _PSS
90*87853babSAni Sinha    testsuite.test("_PSS must be identical for all CPUs", len(uniques) <= 1 or (len(uniques) == 2 and None in uniques))
91*87853babSAni Sinha    for pss, cpupaths in uniques.iteritems():
92*87853babSAni Sinha        if not testsuite.test("_PSS must exist", pss is not None):
93*87853babSAni Sinha            testsuite.print_detail(acpi.factor_commonprefix(cpupaths))
94*87853babSAni Sinha            testsuite.print_detail('No _PSS exists')
95*87853babSAni Sinha            continue
96*87853babSAni Sinha
97*87853babSAni Sinha        if not testsuite.test("_PSS must not be empty", pss.pstates):
98*87853babSAni Sinha            testsuite.print_detail(acpi.factor_commonprefix(cpupaths))
99*87853babSAni Sinha            testsuite.print_detail('_PSS is empty')
100*87853babSAni Sinha            continue
101*87853babSAni Sinha
102*87853babSAni Sinha        testsuite.print_detail(acpi.factor_commonprefix(cpupaths))
103*87853babSAni Sinha        for index, pstate in enumerate(pss.pstates):
104*87853babSAni Sinha            testsuite.print_detail("P[{}]: {}".format(index, pstate))
105*87853babSAni Sinha
106*87853babSAni Sinha        testsuite.test("_PSS must contain at most 16 Pstates", len(pss.pstates) <= 16)
107*87853babSAni Sinha        testsuite.test("_PSS must have no duplicate Pstates", len(pss.pstates) == len(set(pss.pstates)))
108*87853babSAni Sinha
109*87853babSAni Sinha        frequencies = [p.core_frequency for p in pss.pstates]
110*87853babSAni Sinha        testsuite.test("_PSS must list Pstates in descending order of frequency", frequencies == sorted(frequencies, reverse=True))
111*87853babSAni Sinha
112*87853babSAni Sinha        testsuite.test("_PSS must have Pstates with no duplicate frequencies", len(frequencies) == len(set(frequencies)))
113*87853babSAni Sinha
114*87853babSAni Sinha        dissipations = [p.power for p in pss.pstates]
115*87853babSAni Sinha        testsuite.test("_PSS must list Pstates in descending order of power dissipation", dissipations == sorted(dissipations, reverse=True))
116*87853babSAni Sinha
117*87853babSAni Sinhadef test_pstates():
118*87853babSAni Sinha    """Execute and verify frequency for each Pstate in the _PSS"""
119*87853babSAni Sinha    IA32_PERF_CTL = 0x199
120*87853babSAni Sinha    with bits.mwait.use_hint(), bits.preserve_msr(IA32_PERF_CTL):
121*87853babSAni Sinha        cpupath_procid = acpi.find_procid()
122*87853babSAni Sinha        cpupath_uid = acpi.find_uid()
123*87853babSAni Sinha        apic = acpi.parse_apic()
124*87853babSAni Sinha        procid_apicid = apic.procid_apicid
125*87853babSAni Sinha        uid_x2apicid = apic.uid_x2apicid
126*87853babSAni Sinha        def cpupath_apicid(cpupath):
127*87853babSAni Sinha            if procid_apicid is not None:
128*87853babSAni Sinha                procid = cpupath_procid.get(cpupath, None)
129*87853babSAni Sinha                if procid is not None:
130*87853babSAni Sinha                    apicid = procid_apicid.get(procid, None)
131*87853babSAni Sinha                    if apicid is not None:
132*87853babSAni Sinha                        return apicid
133*87853babSAni Sinha            if uid_x2apicid is not None:
134*87853babSAni Sinha                uid = cpupath_uid.get(cpupath, None)
135*87853babSAni Sinha                if uid is not None:
136*87853babSAni Sinha                    apicid = uid_x2apicid.get(uid, None)
137*87853babSAni Sinha                    if apicid is not None:
138*87853babSAni Sinha                        return apicid
139*87853babSAni Sinha            return bits.cpus()[0]
140*87853babSAni Sinha
141*87853babSAni Sinha        bclk = testutil.adjust_to_nearest(bits.bclk(), 100.0/12) * 1000000
142*87853babSAni Sinha
143*87853babSAni Sinha        uniques = acpi.parse_cpu_method("_PSS")
144*87853babSAni Sinha        for pss, cpupaths in uniques.iteritems():
145*87853babSAni Sinha            if not testsuite.test("_PSS must exist", pss is not None):
146*87853babSAni Sinha                testsuite.print_detail(acpi.factor_commonprefix(cpupaths))
147*87853babSAni Sinha                testsuite.print_detail('No _PSS exists')
148*87853babSAni Sinha                continue
149*87853babSAni Sinha
150*87853babSAni Sinha            for n, pstate in enumerate(pss.pstates):
151*87853babSAni Sinha                for cpupath in cpupaths:
152*87853babSAni Sinha                    apicid = cpupath_apicid(cpupath)
153*87853babSAni Sinha                    if apicid is None:
154*87853babSAni Sinha                        print 'Failed to find apicid for cpupath {}'.format(cpupath)
155*87853babSAni Sinha                        continue
156*87853babSAni Sinha                    bits.wrmsr(apicid, IA32_PERF_CTL, pstate.control)
157*87853babSAni Sinha
158*87853babSAni Sinha                # Detecting Turbo frequency requires at least 2 pstates
159*87853babSAni Sinha                # since turbo frequency = max non-turbo frequency + 1
160*87853babSAni Sinha                turbo = False
161*87853babSAni Sinha                if len(pss.pstates) >= 2:
162*87853babSAni Sinha                    turbo = (n == 0 and pstate.core_frequency == (pss.pstates[1].core_frequency + 1))
163*87853babSAni Sinha                    if turbo:
164*87853babSAni Sinha                        # Needs to busywait, not sleep
165*87853babSAni Sinha                        start = time.time()
166*87853babSAni Sinha                        while (time.time() - start < 2):
167*87853babSAni Sinha                            pass
168*87853babSAni Sinha
169*87853babSAni Sinha                for duration in (0.1, 1.0):
170*87853babSAni Sinha                    frequency_data = bits.cpu_frequency(duration)
171*87853babSAni Sinha                    # Abort the test if no cpu frequency is not available
172*87853babSAni Sinha                    if frequency_data is None:
173*87853babSAni Sinha                        continue
174*87853babSAni Sinha                    aperf = frequency_data[1]
175*87853babSAni Sinha                    aperf = testutil.adjust_to_nearest(aperf, bclk/2)
176*87853babSAni Sinha                    aperf = int(aperf / 1000000)
177*87853babSAni Sinha                    if turbo:
178*87853babSAni Sinha                        if aperf >= pstate.core_frequency:
179*87853babSAni Sinha                            break
180*87853babSAni Sinha                    else:
181*87853babSAni Sinha                        if aperf == pstate.core_frequency:
182*87853babSAni Sinha                            break
183*87853babSAni Sinha
184*87853babSAni Sinha                if turbo:
185*87853babSAni Sinha                    testsuite.test("P{}: Turbo measured frequency {} >= expected {} MHz".format(n, aperf, pstate.core_frequency), aperf >= pstate.core_frequency)
186*87853babSAni Sinha                else:
187*87853babSAni Sinha                    testsuite.test("P{}: measured frequency {} MHz == expected {} MHz".format(n, aperf, pstate.core_frequency), aperf == pstate.core_frequency)
188*87853babSAni Sinha
189*87853babSAni Sinhadef test_psd_thread_scope():
190*87853babSAni Sinha    uniques = acpi.parse_cpu_method("_PSD")
191*87853babSAni Sinha    if not testsuite.test("_PSD (P-State Dependency) must exist for each processor", None not in uniques):
192*87853babSAni Sinha        testsuite.print_detail(acpi.factor_commonprefix(uniques[None]))
193*87853babSAni Sinha        testsuite.print_detail('No _PSD exists')
194*87853babSAni Sinha        return
195*87853babSAni Sinha    unique_num_dependencies = {}
196*87853babSAni Sinha    unique_num_entries = {}
197*87853babSAni Sinha    unique_revision = {}
198*87853babSAni Sinha    unique_domain = {}
199*87853babSAni Sinha    unique_coordination_type = {}
200*87853babSAni Sinha    unique_num_processors = {}
201*87853babSAni Sinha    for value, cpupaths in uniques.iteritems():
202*87853babSAni Sinha        unique_num_dependencies.setdefault(len(value.dependencies), []).extend(cpupaths)
203*87853babSAni Sinha        unique_num_entries.setdefault(value.dependencies[0].num_entries, []).extend(cpupaths)
204*87853babSAni Sinha        unique_revision.setdefault(value.dependencies[0].revision, []).extend(cpupaths)
205*87853babSAni Sinha        unique_domain.setdefault(value.dependencies[0].domain, []).extend(cpupaths)
206*87853babSAni Sinha        unique_coordination_type.setdefault(value.dependencies[0].coordination_type, []).extend(cpupaths)
207*87853babSAni Sinha        unique_num_processors.setdefault(value.dependencies[0].num_processors, []).extend(cpupaths)
208*87853babSAni Sinha    def detail(d, fmt):
209*87853babSAni Sinha        for value, cpupaths in sorted(d.iteritems(), key=(lambda (k,v): v)):
210*87853babSAni Sinha            testsuite.print_detail(acpi.factor_commonprefix(cpupaths))
211*87853babSAni Sinha            testsuite.print_detail(fmt.format(value))
212*87853babSAni Sinha
213*87853babSAni Sinha    testsuite.test('Dependency count for each processor must be 1', unique_num_dependencies.keys() == [1])
214*87853babSAni Sinha    detail(unique_num_dependencies, 'Dependency count for each processor = {} (Expected 1)')
215*87853babSAni Sinha    testsuite.test('_PSD.num_entries must be 5', unique_num_entries.keys() == [5])
216*87853babSAni Sinha    detail(unique_num_entries, 'num_entries = {} (Expected 5)')
217*87853babSAni Sinha    testsuite.test('_PSD.revision must be 0', unique_revision.keys() == [0])
218*87853babSAni Sinha    detail(unique_revision, 'revision = {}')
219*87853babSAni Sinha    testsuite.test('_PSD.coordination_type must be 0xFE (HW_ALL)', unique_coordination_type.keys() == [0xfe])
220*87853babSAni Sinha    detail(unique_coordination_type, 'coordination_type = {:#x} (Expected 0xFE HW_ALL)')
221*87853babSAni Sinha    testsuite.test('_PSD.domain must be unique (thread-scoped) for each processor', len(unique_domain) == len(acpi.get_cpupaths()))
222*87853babSAni Sinha    detail(unique_domain, 'domain = {:#x} (Expected a unique value for each processor)')
223*87853babSAni Sinha    testsuite.test('_PSD.num_processors must be 1', unique_num_processors.keys() == [1])
224*87853babSAni Sinha    detail(unique_num_processors, 'num_processors = {} (Expected 1)')
225*87853babSAni Sinha
226*87853babSAni Sinhadef test_table_checksum(data):
227*87853babSAni Sinha    csum = sum(ord(c) for c in data) % 0x100
228*87853babSAni Sinha    testsuite.test('ACPI table cumulative checksum must equal 0', csum == 0)
229*87853babSAni Sinha    testsuite.print_detail("Cumulative checksum = {} (Expected 0)".format(csum))
230*87853babSAni Sinha
231*87853babSAni Sinhadef test_apic():
232*87853babSAni Sinha    data = acpi.get_table("APIC")
233*87853babSAni Sinha    if data is None:
234*87853babSAni Sinha        return
235*87853babSAni Sinha    test_table_checksum(data)
236*87853babSAni Sinha    apic = acpi.parse_apic()
237*87853babSAni Sinha
238*87853babSAni Sinhadef test_dsdt():
239*87853babSAni Sinha    data = acpi.get_table("DSDT")
240*87853babSAni Sinha    if data is None:
241*87853babSAni Sinha        return
242*87853babSAni Sinha    test_table_checksum(data)
243*87853babSAni Sinha
244*87853babSAni Sinhadef test_facp():
245*87853babSAni Sinha    data = acpi.get_table("FACP")
246*87853babSAni Sinha    if data is None:
247*87853babSAni Sinha        return
248*87853babSAni Sinha    test_table_checksum(data)
249*87853babSAni Sinha    facp = acpi.parse_facp()
250*87853babSAni Sinha
251*87853babSAni Sinhadef test_hpet():
252*87853babSAni Sinha    data = acpi.get_table("HPET")
253*87853babSAni Sinha    if data is None:
254*87853babSAni Sinha        return
255*87853babSAni Sinha    test_table_checksum(data)
256*87853babSAni Sinha    hpet = acpi.parse_hpet()
257*87853babSAni Sinha
258*87853babSAni Sinhadef test_mpst():
259*87853babSAni Sinha    data = acpi.get_table("MPST")
260*87853babSAni Sinha    if data is None:
261*87853babSAni Sinha        return
262*87853babSAni Sinha    test_table_checksum(data)
263*87853babSAni Sinha    mpst = acpi.MPST(data)
264*87853babSAni Sinha
265*87853babSAni Sinhadef test_rsdp():
266*87853babSAni Sinha    data = acpi.get_table("RSD PTR ")
267*87853babSAni Sinha    if data is None:
268*87853babSAni Sinha        return
269*87853babSAni Sinha
270*87853babSAni Sinha    # Checksum the first 20 bytes per ACPI 1.0
271*87853babSAni Sinha    csum = sum(ord(c) for c in data[:20]) % 0x100
272*87853babSAni Sinha    testsuite.test('ACPI 1.0 table first 20 bytes cummulative checksum must equal 0', csum == 0)
273*87853babSAni Sinha    testsuite.print_detail("Cummulative checksum = {} (Expected 0)".format(csum))
274*87853babSAni Sinha
275*87853babSAni Sinha    test_table_checksum(data)
276*87853babSAni Sinha    rsdp = acpi.parse_rsdp()
277*87853babSAni Sinha
278*87853babSAni Sinhadef test_xsdt():
279*87853babSAni Sinha    data = acpi.get_table("XSDT")
280*87853babSAni Sinha    if data is None:
281*87853babSAni Sinha        return
282*87853babSAni Sinha    test_table_checksum(data)
283*87853babSAni Sinha    xsdt = acpi.parse_xsdt()
284