Commit d518573d authored by Andreas Herrmann's avatar Andreas Herrmann Committed by Ingo Molnar

x86, amd: Normalize compute unit IDs on multi-node processors

On multi-node CPUs we don't need the socket wide compute unit ID
but the node-wide compute unit ID. Thus we need to normalize the
value. This is similar to what we do with cpu_core_id.

A compute unit is then identified by physical_package_id,
node_id, and compute_unit_id.
Signed-off-by: default avatarAndreas Herrmann <andreas.herrmann3@amd.com>
LKML-Reference: <1295881543-572552-2-git-send-email-hans.rosenfeld@amd.com>
Signed-off-by: default avatarIngo Molnar <mingo@elte.hu>
parent 6663050e
...@@ -261,7 +261,7 @@ static int __cpuinit nearby_node(int apicid) ...@@ -261,7 +261,7 @@ static int __cpuinit nearby_node(int apicid)
#ifdef CONFIG_X86_HT #ifdef CONFIG_X86_HT
static void __cpuinit amd_get_topology(struct cpuinfo_x86 *c) static void __cpuinit amd_get_topology(struct cpuinfo_x86 *c)
{ {
u32 nodes; u32 nodes, cores_per_cu;
u8 node_id; u8 node_id;
int cpu = smp_processor_id(); int cpu = smp_processor_id();
...@@ -276,6 +276,7 @@ static void __cpuinit amd_get_topology(struct cpuinfo_x86 *c) ...@@ -276,6 +276,7 @@ static void __cpuinit amd_get_topology(struct cpuinfo_x86 *c)
/* get compute unit information */ /* get compute unit information */
smp_num_siblings = ((ebx >> 8) & 3) + 1; smp_num_siblings = ((ebx >> 8) & 3) + 1;
c->compute_unit_id = ebx & 0xff; c->compute_unit_id = ebx & 0xff;
cores_per_cu = ((ebx >> 8) & 3) + 1;
} else if (cpu_has(c, X86_FEATURE_NODEID_MSR)) { } else if (cpu_has(c, X86_FEATURE_NODEID_MSR)) {
u64 value; u64 value;
...@@ -288,15 +289,18 @@ static void __cpuinit amd_get_topology(struct cpuinfo_x86 *c) ...@@ -288,15 +289,18 @@ static void __cpuinit amd_get_topology(struct cpuinfo_x86 *c)
/* fixup multi-node processor information */ /* fixup multi-node processor information */
if (nodes > 1) { if (nodes > 1) {
u32 cores_per_node; u32 cores_per_node;
u32 cus_per_node;
set_cpu_cap(c, X86_FEATURE_AMD_DCM); set_cpu_cap(c, X86_FEATURE_AMD_DCM);
cores_per_node = c->x86_max_cores / nodes; cores_per_node = c->x86_max_cores / nodes;
cus_per_node = cores_per_node / cores_per_cu;
/* store NodeID, use llc_shared_map to store sibling info */ /* store NodeID, use llc_shared_map to store sibling info */
per_cpu(cpu_llc_id, cpu) = node_id; per_cpu(cpu_llc_id, cpu) = node_id;
/* core id to be in range from 0 to (cores_per_node - 1) */ /* core id to be in range from 0 to (cores_per_node - 1) */
c->cpu_core_id = c->cpu_core_id % cores_per_node; c->cpu_core_id %= cores_per_node;
c->compute_unit_id %= cus_per_node;
} }
} }
#endif #endif
......
...@@ -414,6 +414,7 @@ void __cpuinit set_cpu_sibling_map(int cpu) ...@@ -414,6 +414,7 @@ void __cpuinit set_cpu_sibling_map(int cpu)
if (cpu_has(c, X86_FEATURE_TOPOEXT)) { if (cpu_has(c, X86_FEATURE_TOPOEXT)) {
if (c->phys_proc_id == o->phys_proc_id && if (c->phys_proc_id == o->phys_proc_id &&
per_cpu(cpu_llc_id, cpu) == per_cpu(cpu_llc_id, i) &&
c->compute_unit_id == o->compute_unit_id) c->compute_unit_id == o->compute_unit_id)
link_thread_siblings(cpu, i); link_thread_siblings(cpu, i);
} else if (c->phys_proc_id == o->phys_proc_id && } else if (c->phys_proc_id == o->phys_proc_id &&
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment