From ca36aedb4e71a1b8e1738f5329ce20b6e83d174d Mon Sep 17 00:00:00 2001 From: Jason Glenesk Date: Tue, 15 Sep 2020 21:01:57 -0700 Subject: acpi: Add SSDT pstate helper functions Add new generic helper functions for PSS, PCT, XPSS, objects. BUG=b:155307433 TEST=Boot Morphius and dump SSDT. Confirm PSS and PCT objects appear as expected and conform to ACPI_6_3_May16.pdf ACPI specification. Check XPSS against Microsoft "Extended PSS ACPI Method Specification" XPSS_spec.doc April 2, 2007. BRANCH=Zork Change-Id: I1ea218bcee33093481e82390550ff96d9d2cb8b5 Signed-off-by: Jason Glenesk Reviewed-on: https://review.coreboot.org/c/coreboot/+/45437 Tested-by: build bot (Jenkins) Reviewed-by: Furquan Shaikh Reviewed-by: Raul Rangel Reviewed-by: Felix Held --- src/acpi/acpigen.c | 57 ++++++++++++++++++++++++++++++++++++++++++++++ src/include/acpi/acpi.h | 20 ++++++++++++++++ src/include/acpi/acpigen.h | 5 ++++ 3 files changed, 82 insertions(+) (limited to 'src') diff --git a/src/acpi/acpigen.c b/src/acpi/acpigen.c index 7910cbcbc1..5b45ebd3a8 100644 --- a/src/acpi/acpigen.c +++ b/src/acpi/acpigen.c @@ -832,6 +832,23 @@ void acpigen_write_PSS_package(u32 coreFreq, u32 power, u32 transLat, coreFreq, power, control, status); } +void acpigen_write_pss_object(const struct acpi_sw_pstate *pstate_values, size_t nentries) +{ + size_t pstate; + + acpigen_write_name("_PSS"); + acpigen_write_package(nentries); + for (pstate = 0; pstate < nentries; pstate++) { + acpigen_write_PSS_package( + pstate_values->core_freq, pstate_values->power, + pstate_values->transition_latency, pstate_values->bus_master_latency, + pstate_values->control_value, pstate_values->status_value); + pstate_values++; + } + + acpigen_pop_len(); +} + void acpigen_write_PSD_package(u32 domain, u32 numprocs, PSD_coord coordtype) { acpigen_write_name("_PSD"); @@ -2002,3 +2019,43 @@ void acpigen_write_create_qword_field(uint8_t op, size_t byte_offset, const char { _create_field(CREATE_QWORD_OP, op, byte_offset, name); } + +void acpigen_write_pct_package(const acpi_addr_t *perf_ctrl, const acpi_addr_t *perf_sts) +{ + acpigen_write_name("_PCT"); + acpigen_write_package(0x02); + acpigen_write_register_resource(perf_ctrl); + acpigen_write_register_resource(perf_sts); + + acpigen_pop_len(); +} + +void acpigen_write_xpss_package(const struct acpi_xpss_sw_pstate *pstate_value) +{ + acpigen_write_package(0x08); + acpigen_write_dword(pstate_value->core_freq); + acpigen_write_dword(pstate_value->power); + acpigen_write_dword(pstate_value->transition_latency); + acpigen_write_dword(pstate_value->bus_master_latency); + + acpigen_write_byte_buffer((uint8_t *)&pstate_value->control_value, sizeof(uint64_t)); + acpigen_write_byte_buffer((uint8_t *)&pstate_value->status_value, sizeof(uint64_t)); + acpigen_write_byte_buffer((uint8_t *)&pstate_value->control_mask, sizeof(uint64_t)); + acpigen_write_byte_buffer((uint8_t *)&pstate_value->status_mask, sizeof(uint64_t)); + + acpigen_pop_len(); +} + +void acpigen_write_xpss_object(const struct acpi_xpss_sw_pstate *pstate_values, size_t nentries) +{ + size_t pstate; + + acpigen_write_name("XPSS"); + acpigen_write_package(nentries); + for (pstate = 0; pstate < nentries; pstate++) { + acpigen_write_xpss_package(pstate_values); + pstate_values++; + } + + acpigen_pop_len(); +} diff --git a/src/include/acpi/acpi.h b/src/include/acpi/acpi.h index 58e1dbe48a..53308f3486 100644 --- a/src/include/acpi/acpi.h +++ b/src/include/acpi/acpi.h @@ -800,6 +800,26 @@ typedef struct acpi_cstate { acpi_addr_t resource; } __packed acpi_cstate_t; +struct acpi_sw_pstate { + u32 core_freq; + u32 power; + u32 transition_latency; + u32 bus_master_latency; + u32 control_value; + u32 status_value; +} __packed; + +struct acpi_xpss_sw_pstate { + u64 core_freq; + u64 power; + u64 transition_latency; + u64 bus_master_latency; + u64 control_value; + u64 status_value; + u64 control_mask; + u64 status_mask; +} __packed; + typedef struct acpi_tstate { u32 percent; u32 power; diff --git a/src/include/acpi/acpigen.h b/src/include/acpi/acpigen.h index e44926f576..c30f8449b6 100644 --- a/src/include/acpi/acpigen.h +++ b/src/include/acpi/acpigen.h @@ -324,6 +324,7 @@ void acpigen_write_STA_ext(const char *namestring); void acpigen_write_TPC(const char *gnvs_tpc_limit); void acpigen_write_PSS_package(u32 coreFreq, u32 power, u32 transLat, u32 busmLat, u32 control, u32 status); +void acpigen_write_pss_object(const struct acpi_sw_pstate *pstate_values, size_t nentries); typedef enum { SW_ALL = 0xfc, SW_ANY = 0xfd, HW_ALL = 0xfe } PSD_coord; void acpigen_write_PSD_package(u32 domain, u32 numprocs, PSD_coord coordtype); void acpigen_write_CST_package_entry(acpi_cstate_t *cstate); @@ -331,6 +332,10 @@ void acpigen_write_CST_package(acpi_cstate_t *entry, int nentries); typedef enum { CSD_HW_ALL = 0xfe } CSD_coord; void acpigen_write_CSD_package(u32 domain, u32 numprocs, CSD_coord coordtype, u32 index); +void acpigen_write_pct_package(const acpi_addr_t *perf_ctrl, const acpi_addr_t *perf_sts); +void acpigen_write_xpss_package(const struct acpi_xpss_sw_pstate *pstate_value); +void acpigen_write_xpss_object(const struct acpi_xpss_sw_pstate *pstate_values, + size_t nentries); void acpigen_write_processor(u8 cpuindex, u32 pblock_addr, u8 pblock_len); void acpigen_write_processor_package(const char *name, unsigned int first_core, -- cgit v1.2.3