aboutsummaryrefslogtreecommitdiffstats
path: root/arch/x86
diff options
context:
space:
mode:
authorPeter P Waskiewicz Jr <peter.p.waskiewicz.jr@intel.com>2015-01-23 13:45:43 -0500
committerIngo Molnar <mingo@kernel.org>2015-02-25 07:53:31 -0500
commitcbc82b17263877ea5d21e84c58ce03f0292458a1 (patch)
tree820d727110dce2682360921535c08677006375ef /arch/x86
parent79dff51e900fd26a073be8b23acfbd8c15edb181 (diff)
x86: Add support for Intel Cache QoS Monitoring (CQM) detection
This patch adds support for the new Cache QoS Monitoring (CQM) feature found in future Intel Xeon processors. It includes the new values to track CQM resources to the cpuinfo_x86 structure, plus the CPUID detection routines for CQM. CQM allows a process, or set of processes, to be tracked by the CPU to determine the cache usage of that task group. Using this data from the CPU, software can be written to extract this data and report cache usage and occupancy for a particular process, or group of processes. More information about Cache QoS Monitoring can be found in the Intel (R) x86 Architecture Software Developer Manual, section 17.14. Signed-off-by: Peter P Waskiewicz Jr <peter.p.waskiewicz.jr@intel.com> Signed-off-by: Matt Fleming <matt.fleming@intel.com> Signed-off-by: Peter Zijlstra (Intel) <peterz@infradead.org> Cc: Andy Lutomirski <luto@amacapital.net> Cc: Arnaldo Carvalho de Melo <acme@kernel.org> Cc: Borislav Petkov <bp@suse.de> Cc: Chris Webb <chris@arachsys.com> Cc: Dave Hansen <dave.hansen@linux.intel.com> Cc: Fenghua Yu <fenghua.yu@intel.com> Cc: H. Peter Anvin <hpa@zytor.com> Cc: Igor Mammedov <imammedo@redhat.com> Cc: Jacob Shin <jacob.w.shin@gmail.com> Cc: Jan Beulich <JBeulich@suse.com> Cc: Jiri Olsa <jolsa@redhat.com> Cc: Kanaka Juvva <kanaka.d.juvva@intel.com> Cc: Linus Torvalds <torvalds@linux-foundation.org> Cc: Steven Honeyman <stevenhoneyman@gmail.com> Cc: Steven Rostedt <srostedt@redhat.com> Cc: Vikas Shivappa <vikas.shivappa@linux.intel.com> Link: http://lkml.kernel.org/r/1422038748-21397-5-git-send-email-matt@codeblueprint.co.uk Signed-off-by: Ingo Molnar <mingo@kernel.org>
Diffstat (limited to 'arch/x86')
-rw-r--r--arch/x86/include/asm/cpufeature.h9
-rw-r--r--arch/x86/include/asm/processor.h3
-rw-r--r--arch/x86/kernel/cpu/common.c39
3 files changed, 50 insertions, 1 deletions
diff --git a/arch/x86/include/asm/cpufeature.h b/arch/x86/include/asm/cpufeature.h
index 90a54851aedc..361922dcc9b1 100644
--- a/arch/x86/include/asm/cpufeature.h
+++ b/arch/x86/include/asm/cpufeature.h
@@ -12,7 +12,7 @@
12#include <asm/disabled-features.h> 12#include <asm/disabled-features.h>
13#endif 13#endif
14 14
15#define NCAPINTS 11 /* N 32-bit words worth of info */ 15#define NCAPINTS 13 /* N 32-bit words worth of info */
16#define NBUGINTS 1 /* N 32-bit bug flags */ 16#define NBUGINTS 1 /* N 32-bit bug flags */
17 17
18/* 18/*
@@ -226,6 +226,7 @@
226#define X86_FEATURE_ERMS ( 9*32+ 9) /* Enhanced REP MOVSB/STOSB */ 226#define X86_FEATURE_ERMS ( 9*32+ 9) /* Enhanced REP MOVSB/STOSB */
227#define X86_FEATURE_INVPCID ( 9*32+10) /* Invalidate Processor Context ID */ 227#define X86_FEATURE_INVPCID ( 9*32+10) /* Invalidate Processor Context ID */
228#define X86_FEATURE_RTM ( 9*32+11) /* Restricted Transactional Memory */ 228#define X86_FEATURE_RTM ( 9*32+11) /* Restricted Transactional Memory */
229#define X86_FEATURE_CQM ( 9*32+12) /* Cache QoS Monitoring */
229#define X86_FEATURE_MPX ( 9*32+14) /* Memory Protection Extension */ 230#define X86_FEATURE_MPX ( 9*32+14) /* Memory Protection Extension */
230#define X86_FEATURE_AVX512F ( 9*32+16) /* AVX-512 Foundation */ 231#define X86_FEATURE_AVX512F ( 9*32+16) /* AVX-512 Foundation */
231#define X86_FEATURE_RDSEED ( 9*32+18) /* The RDSEED instruction */ 232#define X86_FEATURE_RDSEED ( 9*32+18) /* The RDSEED instruction */
@@ -242,6 +243,12 @@
242#define X86_FEATURE_XGETBV1 (10*32+ 2) /* XGETBV with ECX = 1 */ 243#define X86_FEATURE_XGETBV1 (10*32+ 2) /* XGETBV with ECX = 1 */
243#define X86_FEATURE_XSAVES (10*32+ 3) /* XSAVES/XRSTORS */ 244#define X86_FEATURE_XSAVES (10*32+ 3) /* XSAVES/XRSTORS */
244 245
246/* Intel-defined CPU QoS Sub-leaf, CPUID level 0x0000000F:0 (edx), word 11 */
247#define X86_FEATURE_CQM_LLC (11*32+ 1) /* LLC QoS if 1 */
248
249/* Intel-defined CPU QoS Sub-leaf, CPUID level 0x0000000F:1 (edx), word 12 */
250#define X86_FEATURE_CQM_OCCUP_LLC (12*32+ 0) /* LLC occupancy monitoring if 1 */
251
245/* 252/*
246 * BUG word(s) 253 * BUG word(s)
247 */ 254 */
diff --git a/arch/x86/include/asm/processor.h b/arch/x86/include/asm/processor.h
index ec1c93588cef..a12d50e04d7a 100644
--- a/arch/x86/include/asm/processor.h
+++ b/arch/x86/include/asm/processor.h
@@ -109,6 +109,9 @@ struct cpuinfo_x86 {
109 /* in KB - valid for CPUS which support this call: */ 109 /* in KB - valid for CPUS which support this call: */
110 int x86_cache_size; 110 int x86_cache_size;
111 int x86_cache_alignment; /* In bytes */ 111 int x86_cache_alignment; /* In bytes */
112 /* Cache QoS architectural values: */
113 int x86_cache_max_rmid; /* max index */
114 int x86_cache_occ_scale; /* scale to bytes */
112 int x86_power; 115 int x86_power;
113 unsigned long loops_per_jiffy; 116 unsigned long loops_per_jiffy;
114 /* cpuid returned max cores value: */ 117 /* cpuid returned max cores value: */
diff --git a/arch/x86/kernel/cpu/common.c b/arch/x86/kernel/cpu/common.c
index 07f2fc3c13a4..9fa00b2ea0ee 100644
--- a/arch/x86/kernel/cpu/common.c
+++ b/arch/x86/kernel/cpu/common.c
@@ -645,6 +645,30 @@ void get_cpu_cap(struct cpuinfo_x86 *c)
645 c->x86_capability[10] = eax; 645 c->x86_capability[10] = eax;
646 } 646 }
647 647
648 /* Additional Intel-defined flags: level 0x0000000F */
649 if (c->cpuid_level >= 0x0000000F) {
650 u32 eax, ebx, ecx, edx;
651
652 /* QoS sub-leaf, EAX=0Fh, ECX=0 */
653 cpuid_count(0x0000000F, 0, &eax, &ebx, &ecx, &edx);
654 c->x86_capability[11] = edx;
655 if (cpu_has(c, X86_FEATURE_CQM_LLC)) {
656 /* will be overridden if occupancy monitoring exists */
657 c->x86_cache_max_rmid = ebx;
658
659 /* QoS sub-leaf, EAX=0Fh, ECX=1 */
660 cpuid_count(0x0000000F, 1, &eax, &ebx, &ecx, &edx);
661 c->x86_capability[12] = edx;
662 if (cpu_has(c, X86_FEATURE_CQM_OCCUP_LLC)) {
663 c->x86_cache_max_rmid = ecx;
664 c->x86_cache_occ_scale = ebx;
665 }
666 } else {
667 c->x86_cache_max_rmid = -1;
668 c->x86_cache_occ_scale = -1;
669 }
670 }
671
648 /* AMD-defined flags: level 0x80000001 */ 672 /* AMD-defined flags: level 0x80000001 */
649 xlvl = cpuid_eax(0x80000000); 673 xlvl = cpuid_eax(0x80000000);
650 c->extended_cpuid_level = xlvl; 674 c->extended_cpuid_level = xlvl;
@@ -833,6 +857,20 @@ static void generic_identify(struct cpuinfo_x86 *c)
833 detect_nopl(c); 857 detect_nopl(c);
834} 858}
835 859
860static void x86_init_cache_qos(struct cpuinfo_x86 *c)
861{
862 /*
863 * The heavy lifting of max_rmid and cache_occ_scale are handled
864 * in get_cpu_cap(). Here we just set the max_rmid for the boot_cpu
865 * in case CQM bits really aren't there in this CPU.
866 */
867 if (c != &boot_cpu_data) {
868 boot_cpu_data.x86_cache_max_rmid =
869 min(boot_cpu_data.x86_cache_max_rmid,
870 c->x86_cache_max_rmid);
871 }
872}
873
836/* 874/*
837 * This does the hard work of actually picking apart the CPU stuff... 875 * This does the hard work of actually picking apart the CPU stuff...
838 */ 876 */
@@ -922,6 +960,7 @@ static void identify_cpu(struct cpuinfo_x86 *c)
922 960
923 init_hypervisor(c); 961 init_hypervisor(c);
924 x86_init_rdrand(c); 962 x86_init_rdrand(c);
963 x86_init_cache_qos(c);
925 964
926 /* 965 /*
927 * Clear/Set all flags overriden by options, need do it 966 * Clear/Set all flags overriden by options, need do it