From 51676b14e8cfd5bbabf487f659f11704f17f6d0f Mon Sep 17 00:00:00 2001 From: Sven Schnelle Date: Sun, 29 Jul 2012 19:18:03 +0200 Subject: Revert "Use broadcast SIPI to startup siblings" This reverts commit 042c1461fb777e583e5de48edf9326e47ee5595f. It turned out that sending IPIs via broadcast doesn't work on Sandybridge. We tried to come up with a solution, but didn't found any so far. So revert the code for now until we have a working solution. Change-Id: I7dd1cba5a4c1e4b0af366b20e8263b1f6f4b9714 Signed-off-by: Sven Schnelle Reviewed-on: http://review.coreboot.org/1381 Tested-by: build bot (Jenkins) Reviewed-by: Ronald G. Minnich --- src/cpu/intel/hyperthreading/intel_sibling.c | 65 ++++++++++++++++++++++++++++ 1 file changed, 65 insertions(+) (limited to 'src/cpu/intel/hyperthreading/intel_sibling.c') diff --git a/src/cpu/intel/hyperthreading/intel_sibling.c b/src/cpu/intel/hyperthreading/intel_sibling.c index 8377cd0130..b9a9ae7bb1 100644 --- a/src/cpu/intel/hyperthreading/intel_sibling.c +++ b/src/cpu/intel/hyperthreading/intel_sibling.c @@ -7,6 +7,13 @@ #include #include +#if !CONFIG_SERIAL_CPU_INIT +#error Intel hyper-threading requires serialized cpu init +#endif + +static int first_time = 1; +static int disable_siblings = !CONFIG_LOGICAL_CPUS; + /* Return true if running thread does not have the smallest lapic ID * within a CPU core. */ @@ -27,3 +34,61 @@ int intel_ht_sibling(void) threads = (apic_ids / core_ids); return !!(lapicid() & (threads-1)); } + +void intel_sibling_init(device_t cpu) +{ + unsigned i, siblings; + struct cpuid_result result; + + /* On the bootstrap processor see if I want sibling cpus enabled */ + if (first_time) { + first_time = 0; + get_option(&disable_siblings, "hyper_threading"); + } + result = cpuid(1); + /* Is hyperthreading supported */ + if (!(result.edx & (1 << 28))) { + return; + } + /* See how many sibling cpus we have */ + siblings = (result.ebx >> 16) & 0xff; + if (siblings < 1) { + siblings = 1; + } + + printk(BIOS_DEBUG, "CPU: %u %d siblings\n", + cpu->path.apic.apic_id, + siblings); + + /* See if I am a sibling cpu */ + if (cpu->path.apic.apic_id & (siblings -1)) { + if (disable_siblings) { + cpu->enabled = 0; + } + return; + } + + /* I am the primary cpu start up my siblings */ + for(i = 1; i < siblings; i++) { + struct device_path cpu_path; + device_t new; + /* Build the cpu device path */ + cpu_path.type = DEVICE_PATH_APIC; + cpu_path.apic.apic_id = cpu->path.apic.apic_id + i; + + + /* Allocate new cpu device structure iff sibling CPU + * was not in static device tree. + */ + new = alloc_find_dev(cpu->bus, &cpu_path); + + if (!new) { + continue; + } + + printk(BIOS_DEBUG, "CPU: %u has sibling %u\n", + cpu->path.apic.apic_id, + new->path.apic.apic_id); + } +} + -- cgit v1.2.3