diff options
author | H.J. Lu <hjl.tools@gmail.com> | 2016-05-13 07:18:25 -0700 |
---|---|---|
committer | H.J. Lu <hjl.tools@gmail.com> | 2016-05-13 07:18:35 -0700 |
commit | 9e4ec3e81614164314bffe648e9446f17adc5fb7 (patch) | |
tree | e6cf84d13c33651d11aac638e7b46afe5b66bec0 /sysdeps/x86/cacheinfo.c | |
parent | 4cf6c72fd2a482e7499c29162349810029632c3f (diff) | |
download | glibc-9e4ec3e81614164314bffe648e9446f17adc5fb7.tar.gz glibc-9e4ec3e81614164314bffe648e9446f17adc5fb7.tar.xz glibc-9e4ec3e81614164314bffe648e9446f17adc5fb7.zip |
Support non-inclusive caches on Intel processors
* sysdeps/x86/cacheinfo.c (init_cacheinfo): Check and support non-inclusive caches on Intel processors.
Diffstat (limited to 'sysdeps/x86/cacheinfo.c')
-rw-r--r-- | sysdeps/x86/cacheinfo.c | 12 |
1 files changed, 11 insertions, 1 deletions
diff --git a/sysdeps/x86/cacheinfo.c b/sysdeps/x86/cacheinfo.c index 143b3333a8..8408624ea4 100644 --- a/sysdeps/x86/cacheinfo.c +++ b/sysdeps/x86/cacheinfo.c @@ -492,6 +492,9 @@ init_cacheinfo (void) { data = handle_intel (_SC_LEVEL1_DCACHE_SIZE, max_cpuid); + long int core = handle_intel (_SC_LEVEL2_CACHE_SIZE, max_cpuid); + bool inclusive_cache = true; + /* Try L3 first. */ level = 3; shared = handle_intel (_SC_LEVEL3_CACHE_SIZE, max_cpuid); @@ -500,7 +503,7 @@ init_cacheinfo (void) { /* Try L2 otherwise. */ level = 2; - shared = handle_intel (_SC_LEVEL2_CACHE_SIZE, max_cpuid); + shared = core; } /* Figure out the number of logical threads that share the @@ -526,6 +529,9 @@ init_cacheinfo (void) } while (((eax >> 5) & 0x7) != level); + /* Check if cache is inclusive of lower cache levels. */ + inclusive_cache = (edx & 0x2) != 0; + threads = (eax >> 14) & 0x3ff; /* If max_cpuid >= 11, THREADS is the maximum number of @@ -592,6 +598,10 @@ init_cacheinfo (void) threads. */ if (shared > 0 && threads > 0) shared /= threads; + + /* Account for non-inclusive L2 and L3 caches. */ + if (level == 3 && !inclusive_cache) + shared += core; } /* This spells out "AuthenticAMD". */ else if (is_amd) |