aboutsummaryrefslogtreecommitdiffstats
path: root/arch/x86/kernel/smpboot.c
diff options
context:
space:
mode:
Diffstat (limited to 'arch/x86/kernel/smpboot.c')
-rw-r--r--arch/x86/kernel/smpboot.c59
1 files changed, 36 insertions, 23 deletions
diff --git a/arch/x86/kernel/smpboot.c b/arch/x86/kernel/smpboot.c
index 7e52f83d3a4b..7249dcf2cbcb 100644
--- a/arch/x86/kernel/smpboot.c
+++ b/arch/x86/kernel/smpboot.c
@@ -471,7 +471,7 @@ static bool match_die(struct cpuinfo_x86 *c, struct cpuinfo_x86 *o)
471 return false; 471 return false;
472} 472}
473 473
474static struct sched_domain_topology_level numa_inside_package_topology[] = { 474static struct sched_domain_topology_level x86_numa_in_package_topology[] = {
475#ifdef CONFIG_SCHED_SMT 475#ifdef CONFIG_SCHED_SMT
476 { cpu_smt_mask, cpu_smt_flags, SD_INIT_NAME(SMT) }, 476 { cpu_smt_mask, cpu_smt_flags, SD_INIT_NAME(SMT) },
477#endif 477#endif
@@ -480,22 +480,23 @@ static struct sched_domain_topology_level numa_inside_package_topology[] = {
480#endif 480#endif
481 { NULL, }, 481 { NULL, },
482}; 482};
483
484static struct sched_domain_topology_level x86_topology[] = {
485#ifdef CONFIG_SCHED_SMT
486 { cpu_smt_mask, cpu_smt_flags, SD_INIT_NAME(SMT) },
487#endif
488#ifdef CONFIG_SCHED_MC
489 { cpu_coregroup_mask, cpu_core_flags, SD_INIT_NAME(MC) },
490#endif
491 { cpu_cpu_mask, SD_INIT_NAME(DIE) },
492 { NULL, },
493};
494
483/* 495/*
484 * set_sched_topology() sets the topology internal to a CPU. The 496 * Set if a package/die has multiple NUMA nodes inside.
485 * NUMA topologies are layered on top of it to build the full 497 * AMD Magny-Cours and Intel Cluster-on-Die have this.
486 * system topology.
487 *
488 * If NUMA nodes are observed to occur within a CPU package, this
489 * function should be called. It forces the sched domain code to
490 * only use the SMT level for the CPU portion of the topology.
491 * This essentially falls back to relying on NUMA information
492 * from the SRAT table to describe the entire system topology
493 * (except for hyperthreads).
494 */ 498 */
495static void primarily_use_numa_for_topology(void) 499static bool x86_has_numa_in_package;
496{
497 set_sched_topology(numa_inside_package_topology);
498}
499 500
500void set_cpu_sibling_map(int cpu) 501void set_cpu_sibling_map(int cpu)
501{ 502{
@@ -558,7 +559,7 @@ void set_cpu_sibling_map(int cpu)
558 c->booted_cores = cpu_data(i).booted_cores; 559 c->booted_cores = cpu_data(i).booted_cores;
559 } 560 }
560 if (match_die(c, o) && !topology_same_node(c, o)) 561 if (match_die(c, o) && !topology_same_node(c, o))
561 primarily_use_numa_for_topology(); 562 x86_has_numa_in_package = true;
562 } 563 }
563 564
564 threads = cpumask_weight(topology_sibling_cpumask(cpu)); 565 threads = cpumask_weight(topology_sibling_cpumask(cpu));
@@ -690,7 +691,7 @@ wakeup_secondary_cpu_via_nmi(int apicid, unsigned long start_eip)
690 * Give the other CPU some time to accept the IPI. 691 * Give the other CPU some time to accept the IPI.
691 */ 692 */
692 udelay(200); 693 udelay(200);
693 if (APIC_INTEGRATED(apic_version[boot_cpu_physical_apicid])) { 694 if (APIC_INTEGRATED(boot_cpu_apic_version)) {
694 maxlvt = lapic_get_maxlvt(); 695 maxlvt = lapic_get_maxlvt();
695 if (maxlvt > 3) /* Due to the Pentium erratum 3AP. */ 696 if (maxlvt > 3) /* Due to the Pentium erratum 3AP. */
696 apic_write(APIC_ESR, 0); 697 apic_write(APIC_ESR, 0);
@@ -717,7 +718,7 @@ wakeup_secondary_cpu_via_init(int phys_apicid, unsigned long start_eip)
717 /* 718 /*
718 * Be paranoid about clearing APIC errors. 719 * Be paranoid about clearing APIC errors.
719 */ 720 */
720 if (APIC_INTEGRATED(apic_version[phys_apicid])) { 721 if (APIC_INTEGRATED(boot_cpu_apic_version)) {
721 if (maxlvt > 3) /* Due to the Pentium erratum 3AP. */ 722 if (maxlvt > 3) /* Due to the Pentium erratum 3AP. */
722 apic_write(APIC_ESR, 0); 723 apic_write(APIC_ESR, 0);
723 apic_read(APIC_ESR); 724 apic_read(APIC_ESR);
@@ -756,7 +757,7 @@ wakeup_secondary_cpu_via_init(int phys_apicid, unsigned long start_eip)
756 * Determine this based on the APIC version. 757 * Determine this based on the APIC version.
757 * If we don't have an integrated APIC, don't send the STARTUP IPIs. 758 * If we don't have an integrated APIC, don't send the STARTUP IPIs.
758 */ 759 */
759 if (APIC_INTEGRATED(apic_version[phys_apicid])) 760 if (APIC_INTEGRATED(boot_cpu_apic_version))
760 num_starts = 2; 761 num_starts = 2;
761 else 762 else
762 num_starts = 0; 763 num_starts = 0;
@@ -993,7 +994,7 @@ static int do_boot_cpu(int apicid, int cpu, struct task_struct *idle)
993 /* 994 /*
994 * Be paranoid about clearing APIC errors. 995 * Be paranoid about clearing APIC errors.
995 */ 996 */
996 if (APIC_INTEGRATED(apic_version[boot_cpu_physical_apicid])) { 997 if (APIC_INTEGRATED(boot_cpu_apic_version)) {
997 apic_write(APIC_ESR, 0); 998 apic_write(APIC_ESR, 0);
998 apic_read(APIC_ESR); 999 apic_read(APIC_ESR);
999 } 1000 }
@@ -1248,7 +1249,7 @@ static int __init smp_sanity_check(unsigned max_cpus)
1248 /* 1249 /*
1249 * If we couldn't find a local APIC, then get out of here now! 1250 * If we couldn't find a local APIC, then get out of here now!
1250 */ 1251 */
1251 if (APIC_INTEGRATED(apic_version[boot_cpu_physical_apicid]) && 1252 if (APIC_INTEGRATED(boot_cpu_apic_version) &&
1252 !boot_cpu_has(X86_FEATURE_APIC)) { 1253 !boot_cpu_has(X86_FEATURE_APIC)) {
1253 if (!disable_apic) { 1254 if (!disable_apic) {
1254 pr_err("BIOS bug, local APIC #%d not detected!...\n", 1255 pr_err("BIOS bug, local APIC #%d not detected!...\n",
@@ -1303,6 +1304,16 @@ void __init native_smp_prepare_cpus(unsigned int max_cpus)
1303 zalloc_cpumask_var(&per_cpu(cpu_core_map, i), GFP_KERNEL); 1304 zalloc_cpumask_var(&per_cpu(cpu_core_map, i), GFP_KERNEL);
1304 zalloc_cpumask_var(&per_cpu(cpu_llc_shared_map, i), GFP_KERNEL); 1305 zalloc_cpumask_var(&per_cpu(cpu_llc_shared_map, i), GFP_KERNEL);
1305 } 1306 }
1307
1308 /*
1309 * Set 'default' x86 topology, this matches default_topology() in that
1310 * it has NUMA nodes as a topology level. See also
1311 * native_smp_cpus_done().
1312 *
1313 * Must be done before set_cpus_sibling_map() is ran.
1314 */
1315 set_sched_topology(x86_topology);
1316
1306 set_cpu_sibling_map(0); 1317 set_cpu_sibling_map(0);
1307 1318
1308 switch (smp_sanity_check(max_cpus)) { 1319 switch (smp_sanity_check(max_cpus)) {
@@ -1322,14 +1333,13 @@ void __init native_smp_prepare_cpus(unsigned int max_cpus)
1322 break; 1333 break;
1323 } 1334 }
1324 1335
1325 default_setup_apic_routing();
1326
1327 if (read_apic_id() != boot_cpu_physical_apicid) { 1336 if (read_apic_id() != boot_cpu_physical_apicid) {
1328 panic("Boot APIC ID in local APIC unexpected (%d vs %d)", 1337 panic("Boot APIC ID in local APIC unexpected (%d vs %d)",
1329 read_apic_id(), boot_cpu_physical_apicid); 1338 read_apic_id(), boot_cpu_physical_apicid);
1330 /* Or can we switch back to PIC here? */ 1339 /* Or can we switch back to PIC here? */
1331 } 1340 }
1332 1341
1342 default_setup_apic_routing();
1333 cpu0_logical_apicid = apic_bsp_setup(false); 1343 cpu0_logical_apicid = apic_bsp_setup(false);
1334 1344
1335 pr_info("CPU%d: ", 0); 1345 pr_info("CPU%d: ", 0);
@@ -1369,6 +1379,9 @@ void __init native_smp_cpus_done(unsigned int max_cpus)
1369{ 1379{
1370 pr_debug("Boot done\n"); 1380 pr_debug("Boot done\n");
1371 1381
1382 if (x86_has_numa_in_package)
1383 set_sched_topology(x86_numa_in_package_topology);
1384
1372 nmi_selftest(); 1385 nmi_selftest();
1373 impress_friends(); 1386 impress_friends();
1374 setup_ioapic_dest(); 1387 setup_ioapic_dest();