diff options
author | Andi Kleen <ak@suse.de> | 2005-04-16 18:25:15 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@ppc970.osdl.org> | 2005-04-16 18:25:15 -0400 |
commit | 3dd9d514846cdca1dcef2e4fce666d85e199e844 (patch) | |
tree | 28e60a8b733db213e88b0aee8ef3861a93a6fa48 /arch/x86_64/kernel/smpboot.c | |
parent | f2ea2750fbe56867bc8e0eb595115b14195a3e5e (diff) |
[PATCH] x86_64: add support for Intel dual-core detection and displaying
Appended patch adds the support for Intel dual-core detection and displaying
the core related information in /proc/cpuinfo.
It adds two new fields "core id" and "cpu cores" to x86 /proc/cpuinfo and the
"core id" field for x86_64("cpu cores" field is already present in x86_64).
Number of processor cores in a die is detected using cpuid(4) and this is
documented in IA-32 Intel Architecture Software Developer's Manual (vol 2a)
(http://developer.intel.com/design/pentium4/manuals/index_new.htm#sdm_vol2a)
This patch also adds cpu_core_map similar to cpu_sibling_map.
Slightly hacked by AK.
Signed-off-by: Suresh Siddha <suresh.b.siddha@intel.com>
Signed-off-by: Andi Kleen <ak@suse.de>
Signed-off-by: Andrew Morton <akpm@osdl.org>
Signed-off-by: Linus Torvalds <torvalds@osdl.org>
Diffstat (limited to 'arch/x86_64/kernel/smpboot.c')
-rw-r--r-- | arch/x86_64/kernel/smpboot.c | 24 |
1 files changed, 22 insertions, 2 deletions
diff --git a/arch/x86_64/kernel/smpboot.c b/arch/x86_64/kernel/smpboot.c index e5714090b00d..7e2de8925b0f 100644 --- a/arch/x86_64/kernel/smpboot.c +++ b/arch/x86_64/kernel/smpboot.c | |||
@@ -58,7 +58,10 @@ | |||
58 | int smp_num_siblings = 1; | 58 | int smp_num_siblings = 1; |
59 | /* Package ID of each logical CPU */ | 59 | /* Package ID of each logical CPU */ |
60 | u8 phys_proc_id[NR_CPUS] = { [0 ... NR_CPUS-1] = BAD_APICID }; | 60 | u8 phys_proc_id[NR_CPUS] = { [0 ... NR_CPUS-1] = BAD_APICID }; |
61 | /* Core ID of each logical CPU */ | ||
62 | u8 cpu_core_id[NR_CPUS] = { [0 ... NR_CPUS-1] = BAD_APICID }; | ||
61 | EXPORT_SYMBOL(phys_proc_id); | 63 | EXPORT_SYMBOL(phys_proc_id); |
64 | EXPORT_SYMBOL(cpu_core_id); | ||
62 | 65 | ||
63 | /* Bitmask of currently online CPUs */ | 66 | /* Bitmask of currently online CPUs */ |
64 | cpumask_t cpu_online_map; | 67 | cpumask_t cpu_online_map; |
@@ -71,6 +74,7 @@ static cpumask_t smp_commenced_mask; | |||
71 | struct cpuinfo_x86 cpu_data[NR_CPUS] __cacheline_aligned; | 74 | struct cpuinfo_x86 cpu_data[NR_CPUS] __cacheline_aligned; |
72 | 75 | ||
73 | cpumask_t cpu_sibling_map[NR_CPUS] __cacheline_aligned; | 76 | cpumask_t cpu_sibling_map[NR_CPUS] __cacheline_aligned; |
77 | cpumask_t cpu_core_map[NR_CPUS] __cacheline_aligned; | ||
74 | 78 | ||
75 | /* | 79 | /* |
76 | * Trampoline 80x86 program as an array. | 80 | * Trampoline 80x86 program as an array. |
@@ -713,6 +717,7 @@ static void __init smp_boot_cpus(unsigned int max_cpus) | |||
713 | io_apic_irqs = 0; | 717 | io_apic_irqs = 0; |
714 | cpu_online_map = cpumask_of_cpu(0); | 718 | cpu_online_map = cpumask_of_cpu(0); |
715 | cpu_set(0, cpu_sibling_map[0]); | 719 | cpu_set(0, cpu_sibling_map[0]); |
720 | cpu_set(0, cpu_core_map[0]); | ||
716 | phys_cpu_present_map = physid_mask_of_physid(0); | 721 | phys_cpu_present_map = physid_mask_of_physid(0); |
717 | if (APIC_init_uniprocessor()) | 722 | if (APIC_init_uniprocessor()) |
718 | printk(KERN_NOTICE "Local APIC not detected." | 723 | printk(KERN_NOTICE "Local APIC not detected." |
@@ -740,6 +745,7 @@ static void __init smp_boot_cpus(unsigned int max_cpus) | |||
740 | io_apic_irqs = 0; | 745 | io_apic_irqs = 0; |
741 | cpu_online_map = cpumask_of_cpu(0); | 746 | cpu_online_map = cpumask_of_cpu(0); |
742 | cpu_set(0, cpu_sibling_map[0]); | 747 | cpu_set(0, cpu_sibling_map[0]); |
748 | cpu_set(0, cpu_core_map[0]); | ||
743 | phys_cpu_present_map = physid_mask_of_physid(0); | 749 | phys_cpu_present_map = physid_mask_of_physid(0); |
744 | disable_apic = 1; | 750 | disable_apic = 1; |
745 | goto smp_done; | 751 | goto smp_done; |
@@ -756,6 +762,7 @@ static void __init smp_boot_cpus(unsigned int max_cpus) | |||
756 | io_apic_irqs = 0; | 762 | io_apic_irqs = 0; |
757 | cpu_online_map = cpumask_of_cpu(0); | 763 | cpu_online_map = cpumask_of_cpu(0); |
758 | cpu_set(0, cpu_sibling_map[0]); | 764 | cpu_set(0, cpu_sibling_map[0]); |
765 | cpu_set(0, cpu_core_map[0]); | ||
759 | phys_cpu_present_map = physid_mask_of_physid(0); | 766 | phys_cpu_present_map = physid_mask_of_physid(0); |
760 | disable_apic = 1; | 767 | disable_apic = 1; |
761 | goto smp_done; | 768 | goto smp_done; |
@@ -833,10 +840,13 @@ static void __init smp_boot_cpus(unsigned int max_cpus) | |||
833 | * Construct cpu_sibling_map[], so that we can tell the | 840 | * Construct cpu_sibling_map[], so that we can tell the |
834 | * sibling CPU efficiently. | 841 | * sibling CPU efficiently. |
835 | */ | 842 | */ |
836 | for (cpu = 0; cpu < NR_CPUS; cpu++) | 843 | for (cpu = 0; cpu < NR_CPUS; cpu++) { |
837 | cpus_clear(cpu_sibling_map[cpu]); | 844 | cpus_clear(cpu_sibling_map[cpu]); |
845 | cpus_clear(cpu_core_map[cpu]); | ||
846 | } | ||
838 | 847 | ||
839 | for (cpu = 0; cpu < NR_CPUS; cpu++) { | 848 | for (cpu = 0; cpu < NR_CPUS; cpu++) { |
849 | struct cpuinfo_x86 *c = cpu_data + cpu; | ||
840 | int siblings = 0; | 850 | int siblings = 0; |
841 | int i; | 851 | int i; |
842 | if (!cpu_isset(cpu, cpu_callout_map)) | 852 | if (!cpu_isset(cpu, cpu_callout_map)) |
@@ -846,7 +856,7 @@ static void __init smp_boot_cpus(unsigned int max_cpus) | |||
846 | for (i = 0; i < NR_CPUS; i++) { | 856 | for (i = 0; i < NR_CPUS; i++) { |
847 | if (!cpu_isset(i, cpu_callout_map)) | 857 | if (!cpu_isset(i, cpu_callout_map)) |
848 | continue; | 858 | continue; |
849 | if (phys_proc_id[cpu] == phys_proc_id[i]) { | 859 | if (phys_proc_id[cpu] == cpu_core_id[i]) { |
850 | siblings++; | 860 | siblings++; |
851 | cpu_set(i, cpu_sibling_map[cpu]); | 861 | cpu_set(i, cpu_sibling_map[cpu]); |
852 | } | 862 | } |
@@ -862,6 +872,16 @@ static void __init smp_boot_cpus(unsigned int max_cpus) | |||
862 | siblings, cpu, smp_num_siblings); | 872 | siblings, cpu, smp_num_siblings); |
863 | smp_num_siblings = siblings; | 873 | smp_num_siblings = siblings; |
864 | } | 874 | } |
875 | if (c->x86_num_cores > 1) { | ||
876 | for (i = 0; i < NR_CPUS; i++) { | ||
877 | if (!cpu_isset(i, cpu_callout_map)) | ||
878 | continue; | ||
879 | if (phys_proc_id[cpu] == phys_proc_id[i]) { | ||
880 | cpu_set(i, cpu_core_map[cpu]); | ||
881 | } | ||
882 | } | ||
883 | } else | ||
884 | cpu_core_map[cpu] = cpu_sibling_map[cpu]; | ||
865 | } | 885 | } |
866 | 886 | ||
867 | Dprintk("Boot done.\n"); | 887 | Dprintk("Boot done.\n"); |