diff options
-rw-r--r-- | arch/x86/events/amd/uncore.c | 19 |
1 files changed, 16 insertions, 3 deletions
diff --git a/arch/x86/events/amd/uncore.c b/arch/x86/events/amd/uncore.c index e34f8a6b4440..f5cbbba99283 100644 --- a/arch/x86/events/amd/uncore.c +++ b/arch/x86/events/amd/uncore.c | |||
@@ -400,11 +400,24 @@ static int amd_uncore_cpu_starting(unsigned int cpu) | |||
400 | 400 | ||
401 | if (amd_uncore_llc) { | 401 | if (amd_uncore_llc) { |
402 | unsigned int apicid = cpu_data(cpu).apicid; | 402 | unsigned int apicid = cpu_data(cpu).apicid; |
403 | unsigned int nshared; | 403 | unsigned int nshared, subleaf, prev_eax = 0; |
404 | 404 | ||
405 | uncore = *per_cpu_ptr(amd_uncore_llc, cpu); | 405 | uncore = *per_cpu_ptr(amd_uncore_llc, cpu); |
406 | cpuid_count(0x8000001d, 2, &eax, &ebx, &ecx, &edx); | 406 | /* |
407 | nshared = ((eax >> 14) & 0xfff) + 1; | 407 | * Iterate over Cache Topology Definition leaves until no |
408 | * more cache descriptions are available. | ||
409 | */ | ||
410 | for (subleaf = 0; subleaf < 5; subleaf++) { | ||
411 | cpuid_count(0x8000001d, subleaf, &eax, &ebx, &ecx, &edx); | ||
412 | |||
413 | /* EAX[0:4] gives type of cache */ | ||
414 | if (!(eax & 0x1f)) | ||
415 | break; | ||
416 | |||
417 | prev_eax = eax; | ||
418 | } | ||
419 | nshared = ((prev_eax >> 14) & 0xfff) + 1; | ||
420 | |||
408 | uncore->id = apicid - (apicid % nshared); | 421 | uncore->id = apicid - (apicid % nshared); |
409 | 422 | ||
410 | uncore = amd_uncore_find_online_sibling(uncore, amd_uncore_llc); | 423 | uncore = amd_uncore_find_online_sibling(uncore, amd_uncore_llc); |