summaryrefslogtreecommitdiff
path: root/src/soc/intel/common/block/acpi
diff options
context:
space:
mode:
authorSridahr Siricilla <sridhar.siricilla@intel.com>2021-11-11 01:29:40 +0530
committerFelix Held <felix-coreboot@felixheld.de>2022-01-19 21:01:13 +0000
commitcd1cd8d1176cf65f189f0346679c3f4e4fe9af92 (patch)
treef1d16ef702e31831d61ba11e3167698e03d2be33 /src/soc/intel/common/block/acpi
parentcdd025202807b6c520966586310ee6088012de21 (diff)
soc/intel/alderlake: Add method to determine the cpu type
set_cpu_type(): It determines the CPU type (big or small) that is executing the function, and marks the global_cpu_type's array slot which is corresponds to the executing CPU's index if the CPU type is big core. get_cpu_index(): It determines the index from LAPIC Ids. This is required to expose CPPC3 package in ascending order of CPUs' LAPIC ids. So, the function returns CPU's position from the ascending order list of LAPIC ids. TEST=Tested CPU index calculation, core type determination on Brya Signed-off-by: Sridhar Siricilla <sridhar.siricilla@intel.com> Change-Id: If4ceb24d9bb1e808750bf618c29b2b9ea6d4191b Reviewed-on: https://review.coreboot.org/c/coreboot/+/59360 Tested-by: build bot (Jenkins) <no-reply@coreboot.org> Reviewed-by: Tim Wawrzynczak <twawrzynczak@chromium.org>
Diffstat (limited to 'src/soc/intel/common/block/acpi')
-rw-r--r--src/soc/intel/common/block/acpi/Kconfig5
-rw-r--r--src/soc/intel/common/block/acpi/Makefile.inc1
-rw-r--r--src/soc/intel/common/block/acpi/cpu_hybrid.c59
3 files changed, 65 insertions, 0 deletions
diff --git a/src/soc/intel/common/block/acpi/Kconfig b/src/soc/intel/common/block/acpi/Kconfig
index 07e9bea8d3..e21584c073 100644
--- a/src/soc/intel/common/block/acpi/Kconfig
+++ b/src/soc/intel/common/block/acpi/Kconfig
@@ -44,4 +44,9 @@ config SOC_INTEL_COMMON_BLOCK_ACPI_CPPC
help
Generate CPPC entries for Intel SpeedShift
+config SOC_INTEL_COMMON_BLOCK_ACPI_CPU_HYBRID
+ bool
+ help
+ Defines hybrid CPU specific ACPI helper functions.
+
endif
diff --git a/src/soc/intel/common/block/acpi/Makefile.inc b/src/soc/intel/common/block/acpi/Makefile.inc
index a6eb80db36..0286d942dc 100644
--- a/src/soc/intel/common/block/acpi/Makefile.inc
+++ b/src/soc/intel/common/block/acpi/Makefile.inc
@@ -5,3 +5,4 @@ ramstage-$(CONFIG_ACPI_BERT) += acpi_bert.c
ramstage-$(CONFIG_SOC_INTEL_COMMON_ACPI_WAKE_SOURCE) += acpi_wake_source.c
ramstage-$(CONFIG_SOC_INTEL_COMMON_BLOCK_ACPI_PEP) += pep.c
ramstage-$(CONFIG_SOC_INTEL_COMMON_BLOCK_SGX_ENABLE) += sgx.c
+ramstage-$(CONFIG_SOC_INTEL_COMMON_BLOCK_ACPI_CPU_HYBRID) += cpu_hybrid.c
diff --git a/src/soc/intel/common/block/acpi/cpu_hybrid.c b/src/soc/intel/common/block/acpi/cpu_hybrid.c
new file mode 100644
index 0000000000..cbfaed8fd3
--- /dev/null
+++ b/src/soc/intel/common/block/acpi/cpu_hybrid.c
@@ -0,0 +1,59 @@
+/* SPDX-License-Identifier: GPL-2.0-or-later */
+#include <acpi/acpigen.h>
+#include <intelblocks/acpi.h>
+#include <soc/cpu.h>
+#include <smp/spinlock.h>
+#include <device/device.h>
+#include <device/path.h>
+#include <cpu/x86/lapic.h>
+#include <cpu/x86/mp.h>
+
+DECLARE_SPIN_LOCK(cpu_lock);
+static u8 global_cpu_type[CONFIG_MAX_CPUS];
+
+static bool is_big_core(void)
+{
+ return get_soc_cpu_type() == CPUID_CORE_TYPE_INTEL_CORE;
+}
+
+static u32 get_cpu_index(void)
+{
+ u32 cpu_index = 0;
+ struct device *dev;
+ u32 my_apic_id = lapicid();
+
+ for (dev = dev_find_lapic(0); dev; dev = dev->next) {
+ if (my_apic_id > dev->path.apic.apic_id)
+ cpu_index++;
+ }
+
+ return cpu_index;
+}
+
+/*
+ * This function determines the type (big or small) of the CPU that is executing
+ * it and stores the information (in a thread-safe manner) in an global_cpu_type
+ * array.
+ * It requires the SoC to implement a function `get_soc_cpu_type()` which will be
+ * called in a critical section to determine the type of the executing CPU.
+ */
+static void set_cpu_type(void *unused)
+{
+ spin_lock(&cpu_lock);
+ u8 cpu_index = get_cpu_index();
+
+ if (is_big_core())
+ global_cpu_type[cpu_index] = 1;
+
+ spin_unlock(&cpu_lock);
+}
+
+static void run_set_cpu_type(void *unused)
+{
+ if (mp_run_on_all_cpus(set_cpu_type, NULL) != CB_SUCCESS) {
+ printk(BIOS_ERR, "cpu_hybrid: Failed to set global_cpu_type with CPU type info\n");
+ return;
+ }
+}
+
+BOOT_STATE_INIT_ENTRY(BS_DEV_INIT_CHIPS, BS_ON_EXIT, run_set_cpu_type, NULL);