4 * Copyright(c) 2010-2014 Intel Corporation. All rights reserved.
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
11 * * Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * * Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in
15 * the documentation and/or other materials provided with the
17 * * Neither the name of Intel Corporation nor the names of its
18 * contributors may be used to endorse or promote products derived
19 * from this software without specific prior written permission.
21 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
24 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
25 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
26 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
27 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
28 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
29 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
30 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
31 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
34 #ifndef _RTE_CPUFLAGS_X86_64_H_
35 #define _RTE_CPUFLAGS_X86_64_H_
46 #include "generic/rte_cpuflags.h"
49 /* (EAX 01h) ECX features*/
50 RTE_CPUFLAG_SSE3 = 0, /**< SSE3 */
51 RTE_CPUFLAG_PCLMULQDQ, /**< PCLMULQDQ */
52 RTE_CPUFLAG_DTES64, /**< DTES64 */
53 RTE_CPUFLAG_MONITOR, /**< MONITOR */
54 RTE_CPUFLAG_DS_CPL, /**< DS_CPL */
55 RTE_CPUFLAG_VMX, /**< VMX */
56 RTE_CPUFLAG_SMX, /**< SMX */
57 RTE_CPUFLAG_EIST, /**< EIST */
58 RTE_CPUFLAG_TM2, /**< TM2 */
59 RTE_CPUFLAG_SSSE3, /**< SSSE3 */
60 RTE_CPUFLAG_CNXT_ID, /**< CNXT_ID */
61 RTE_CPUFLAG_FMA, /**< FMA */
62 RTE_CPUFLAG_CMPXCHG16B, /**< CMPXCHG16B */
63 RTE_CPUFLAG_XTPR, /**< XTPR */
64 RTE_CPUFLAG_PDCM, /**< PDCM */
65 RTE_CPUFLAG_PCID, /**< PCID */
66 RTE_CPUFLAG_DCA, /**< DCA */
67 RTE_CPUFLAG_SSE4_1, /**< SSE4_1 */
68 RTE_CPUFLAG_SSE4_2, /**< SSE4_2 */
69 RTE_CPUFLAG_X2APIC, /**< X2APIC */
70 RTE_CPUFLAG_MOVBE, /**< MOVBE */
71 RTE_CPUFLAG_POPCNT, /**< POPCNT */
72 RTE_CPUFLAG_TSC_DEADLINE, /**< TSC_DEADLINE */
73 RTE_CPUFLAG_AES, /**< AES */
74 RTE_CPUFLAG_XSAVE, /**< XSAVE */
75 RTE_CPUFLAG_OSXSAVE, /**< OSXSAVE */
76 RTE_CPUFLAG_AVX, /**< AVX */
77 RTE_CPUFLAG_F16C, /**< F16C */
78 RTE_CPUFLAG_RDRAND, /**< RDRAND */
80 /* (EAX 01h) EDX features */
81 RTE_CPUFLAG_FPU, /**< FPU */
82 RTE_CPUFLAG_VME, /**< VME */
83 RTE_CPUFLAG_DE, /**< DE */
84 RTE_CPUFLAG_PSE, /**< PSE */
85 RTE_CPUFLAG_TSC, /**< TSC */
86 RTE_CPUFLAG_MSR, /**< MSR */
87 RTE_CPUFLAG_PAE, /**< PAE */
88 RTE_CPUFLAG_MCE, /**< MCE */
89 RTE_CPUFLAG_CX8, /**< CX8 */
90 RTE_CPUFLAG_APIC, /**< APIC */
91 RTE_CPUFLAG_SEP, /**< SEP */
92 RTE_CPUFLAG_MTRR, /**< MTRR */
93 RTE_CPUFLAG_PGE, /**< PGE */
94 RTE_CPUFLAG_MCA, /**< MCA */
95 RTE_CPUFLAG_CMOV, /**< CMOV */
96 RTE_CPUFLAG_PAT, /**< PAT */
97 RTE_CPUFLAG_PSE36, /**< PSE36 */
98 RTE_CPUFLAG_PSN, /**< PSN */
99 RTE_CPUFLAG_CLFSH, /**< CLFSH */
100 RTE_CPUFLAG_DS, /**< DS */
101 RTE_CPUFLAG_ACPI, /**< ACPI */
102 RTE_CPUFLAG_MMX, /**< MMX */
103 RTE_CPUFLAG_FXSR, /**< FXSR */
104 RTE_CPUFLAG_SSE, /**< SSE */
105 RTE_CPUFLAG_SSE2, /**< SSE2 */
106 RTE_CPUFLAG_SS, /**< SS */
107 RTE_CPUFLAG_HTT, /**< HTT */
108 RTE_CPUFLAG_TM, /**< TM */
109 RTE_CPUFLAG_PBE, /**< PBE */
111 /* (EAX 06h) EAX features */
112 RTE_CPUFLAG_DIGTEMP, /**< DIGTEMP */
113 RTE_CPUFLAG_TRBOBST, /**< TRBOBST */
114 RTE_CPUFLAG_ARAT, /**< ARAT */
115 RTE_CPUFLAG_PLN, /**< PLN */
116 RTE_CPUFLAG_ECMD, /**< ECMD */
117 RTE_CPUFLAG_PTM, /**< PTM */
119 /* (EAX 06h) ECX features */
120 RTE_CPUFLAG_MPERF_APERF_MSR, /**< MPERF_APERF_MSR */
121 RTE_CPUFLAG_ACNT2, /**< ACNT2 */
122 RTE_CPUFLAG_ENERGY_EFF, /**< ENERGY_EFF */
124 /* (EAX 07h, ECX 0h) EBX features */
125 RTE_CPUFLAG_FSGSBASE, /**< FSGSBASE */
126 RTE_CPUFLAG_BMI1, /**< BMI1 */
127 RTE_CPUFLAG_HLE, /**< Hardware Lock elision */
128 RTE_CPUFLAG_AVX2, /**< AVX2 */
129 RTE_CPUFLAG_SMEP, /**< SMEP */
130 RTE_CPUFLAG_BMI2, /**< BMI2 */
131 RTE_CPUFLAG_ERMS, /**< ERMS */
132 RTE_CPUFLAG_INVPCID, /**< INVPCID */
133 RTE_CPUFLAG_RTM, /**< Transactional memory */
135 /* (EAX 80000001h) ECX features */
136 RTE_CPUFLAG_LAHF_SAHF, /**< LAHF_SAHF */
137 RTE_CPUFLAG_LZCNT, /**< LZCNT */
139 /* (EAX 80000001h) EDX features */
140 RTE_CPUFLAG_SYSCALL, /**< SYSCALL */
141 RTE_CPUFLAG_XD, /**< XD */
142 RTE_CPUFLAG_1GB_PG, /**< 1GB_PG */
143 RTE_CPUFLAG_RDTSCP, /**< RDTSCP */
144 RTE_CPUFLAG_EM64T, /**< EM64T */
146 /* (EAX 80000007h) EDX features */
147 RTE_CPUFLAG_INVTSC, /**< INVTSC */
150 RTE_CPUFLAG_NUMFLAGS, /**< This should always be the last! */
153 enum cpu_register_t {
160 static const struct feature_entry cpu_feature_table[] = {
161 FEAT_DEF(SSE3, 0x00000001, 0, RTE_REG_ECX, 0)
162 FEAT_DEF(PCLMULQDQ, 0x00000001, 0, RTE_REG_ECX, 1)
163 FEAT_DEF(DTES64, 0x00000001, 0, RTE_REG_ECX, 2)
164 FEAT_DEF(MONITOR, 0x00000001, 0, RTE_REG_ECX, 3)
165 FEAT_DEF(DS_CPL, 0x00000001, 0, RTE_REG_ECX, 4)
166 FEAT_DEF(VMX, 0x00000001, 0, RTE_REG_ECX, 5)
167 FEAT_DEF(SMX, 0x00000001, 0, RTE_REG_ECX, 6)
168 FEAT_DEF(EIST, 0x00000001, 0, RTE_REG_ECX, 7)
169 FEAT_DEF(TM2, 0x00000001, 0, RTE_REG_ECX, 8)
170 FEAT_DEF(SSSE3, 0x00000001, 0, RTE_REG_ECX, 9)
171 FEAT_DEF(CNXT_ID, 0x00000001, 0, RTE_REG_ECX, 10)
172 FEAT_DEF(FMA, 0x00000001, 0, RTE_REG_ECX, 12)
173 FEAT_DEF(CMPXCHG16B, 0x00000001, 0, RTE_REG_ECX, 13)
174 FEAT_DEF(XTPR, 0x00000001, 0, RTE_REG_ECX, 14)
175 FEAT_DEF(PDCM, 0x00000001, 0, RTE_REG_ECX, 15)
176 FEAT_DEF(PCID, 0x00000001, 0, RTE_REG_ECX, 17)
177 FEAT_DEF(DCA, 0x00000001, 0, RTE_REG_ECX, 18)
178 FEAT_DEF(SSE4_1, 0x00000001, 0, RTE_REG_ECX, 19)
179 FEAT_DEF(SSE4_2, 0x00000001, 0, RTE_REG_ECX, 20)
180 FEAT_DEF(X2APIC, 0x00000001, 0, RTE_REG_ECX, 21)
181 FEAT_DEF(MOVBE, 0x00000001, 0, RTE_REG_ECX, 22)
182 FEAT_DEF(POPCNT, 0x00000001, 0, RTE_REG_ECX, 23)
183 FEAT_DEF(TSC_DEADLINE, 0x00000001, 0, RTE_REG_ECX, 24)
184 FEAT_DEF(AES, 0x00000001, 0, RTE_REG_ECX, 25)
185 FEAT_DEF(XSAVE, 0x00000001, 0, RTE_REG_ECX, 26)
186 FEAT_DEF(OSXSAVE, 0x00000001, 0, RTE_REG_ECX, 27)
187 FEAT_DEF(AVX, 0x00000001, 0, RTE_REG_ECX, 28)
188 FEAT_DEF(F16C, 0x00000001, 0, RTE_REG_ECX, 29)
189 FEAT_DEF(RDRAND, 0x00000001, 0, RTE_REG_ECX, 30)
191 FEAT_DEF(FPU, 0x00000001, 0, RTE_REG_EDX, 0)
192 FEAT_DEF(VME, 0x00000001, 0, RTE_REG_EDX, 1)
193 FEAT_DEF(DE, 0x00000001, 0, RTE_REG_EDX, 2)
194 FEAT_DEF(PSE, 0x00000001, 0, RTE_REG_EDX, 3)
195 FEAT_DEF(TSC, 0x00000001, 0, RTE_REG_EDX, 4)
196 FEAT_DEF(MSR, 0x00000001, 0, RTE_REG_EDX, 5)
197 FEAT_DEF(PAE, 0x00000001, 0, RTE_REG_EDX, 6)
198 FEAT_DEF(MCE, 0x00000001, 0, RTE_REG_EDX, 7)
199 FEAT_DEF(CX8, 0x00000001, 0, RTE_REG_EDX, 8)
200 FEAT_DEF(APIC, 0x00000001, 0, RTE_REG_EDX, 9)
201 FEAT_DEF(SEP, 0x00000001, 0, RTE_REG_EDX, 11)
202 FEAT_DEF(MTRR, 0x00000001, 0, RTE_REG_EDX, 12)
203 FEAT_DEF(PGE, 0x00000001, 0, RTE_REG_EDX, 13)
204 FEAT_DEF(MCA, 0x00000001, 0, RTE_REG_EDX, 14)
205 FEAT_DEF(CMOV, 0x00000001, 0, RTE_REG_EDX, 15)
206 FEAT_DEF(PAT, 0x00000001, 0, RTE_REG_EDX, 16)
207 FEAT_DEF(PSE36, 0x00000001, 0, RTE_REG_EDX, 17)
208 FEAT_DEF(PSN, 0x00000001, 0, RTE_REG_EDX, 18)
209 FEAT_DEF(CLFSH, 0x00000001, 0, RTE_REG_EDX, 19)
210 FEAT_DEF(DS, 0x00000001, 0, RTE_REG_EDX, 21)
211 FEAT_DEF(ACPI, 0x00000001, 0, RTE_REG_EDX, 22)
212 FEAT_DEF(MMX, 0x00000001, 0, RTE_REG_EDX, 23)
213 FEAT_DEF(FXSR, 0x00000001, 0, RTE_REG_EDX, 24)
214 FEAT_DEF(SSE, 0x00000001, 0, RTE_REG_EDX, 25)
215 FEAT_DEF(SSE2, 0x00000001, 0, RTE_REG_EDX, 26)
216 FEAT_DEF(SS, 0x00000001, 0, RTE_REG_EDX, 27)
217 FEAT_DEF(HTT, 0x00000001, 0, RTE_REG_EDX, 28)
218 FEAT_DEF(TM, 0x00000001, 0, RTE_REG_EDX, 29)
219 FEAT_DEF(PBE, 0x00000001, 0, RTE_REG_EDX, 31)
221 FEAT_DEF(DIGTEMP, 0x00000006, 0, RTE_REG_EAX, 0)
222 FEAT_DEF(TRBOBST, 0x00000006, 0, RTE_REG_EAX, 1)
223 FEAT_DEF(ARAT, 0x00000006, 0, RTE_REG_EAX, 2)
224 FEAT_DEF(PLN, 0x00000006, 0, RTE_REG_EAX, 4)
225 FEAT_DEF(ECMD, 0x00000006, 0, RTE_REG_EAX, 5)
226 FEAT_DEF(PTM, 0x00000006, 0, RTE_REG_EAX, 6)
228 FEAT_DEF(MPERF_APERF_MSR, 0x00000006, 0, RTE_REG_ECX, 0)
229 FEAT_DEF(ACNT2, 0x00000006, 0, RTE_REG_ECX, 1)
230 FEAT_DEF(ENERGY_EFF, 0x00000006, 0, RTE_REG_ECX, 3)
232 FEAT_DEF(FSGSBASE, 0x00000007, 0, RTE_REG_EBX, 0)
233 FEAT_DEF(BMI1, 0x00000007, 0, RTE_REG_EBX, 2)
234 FEAT_DEF(HLE, 0x00000007, 0, RTE_REG_EBX, 4)
235 FEAT_DEF(AVX2, 0x00000007, 0, RTE_REG_EBX, 5)
236 FEAT_DEF(SMEP, 0x00000007, 0, RTE_REG_EBX, 6)
237 FEAT_DEF(BMI2, 0x00000007, 0, RTE_REG_EBX, 7)
238 FEAT_DEF(ERMS, 0x00000007, 0, RTE_REG_EBX, 8)
239 FEAT_DEF(INVPCID, 0x00000007, 0, RTE_REG_EBX, 10)
240 FEAT_DEF(RTM, 0x00000007, 0, RTE_REG_EBX, 11)
242 FEAT_DEF(LAHF_SAHF, 0x80000001, 0, RTE_REG_ECX, 0)
243 FEAT_DEF(LZCNT, 0x80000001, 0, RTE_REG_ECX, 4)
245 FEAT_DEF(SYSCALL, 0x80000001, 0, RTE_REG_EDX, 11)
246 FEAT_DEF(XD, 0x80000001, 0, RTE_REG_EDX, 20)
247 FEAT_DEF(1GB_PG, 0x80000001, 0, RTE_REG_EDX, 26)
248 FEAT_DEF(RDTSCP, 0x80000001, 0, RTE_REG_EDX, 27)
249 FEAT_DEF(EM64T, 0x80000001, 0, RTE_REG_EDX, 29)
251 FEAT_DEF(INVTSC, 0x80000007, 0, RTE_REG_EDX, 8)
255 rte_cpu_get_features(uint32_t leaf, uint32_t subleaf, cpuid_registers_t out)
257 #if defined(__i386__) && defined(__PIC__)
258 /* %ebx is a forbidden register if we compile with -fPIC or -fPIE */
259 asm volatile("movl %%ebx,%0 ; cpuid ; xchgl %%ebx,%0"
260 : "=r" (out[RTE_REG_EBX]),
261 "=a" (out[RTE_REG_EAX]),
262 "=c" (out[RTE_REG_ECX]),
263 "=d" (out[RTE_REG_EDX])
264 : "a" (leaf), "c" (subleaf));
268 : "=a" (out[RTE_REG_EAX]),
269 "=b" (out[RTE_REG_EBX]),
270 "=c" (out[RTE_REG_ECX]),
271 "=d" (out[RTE_REG_EDX])
272 : "a" (leaf), "c" (subleaf));
278 rte_cpu_get_flag_enabled(enum rte_cpu_flag_t feature)
280 const struct feature_entry *feat;
281 cpuid_registers_t regs;
284 if (feature >= RTE_CPUFLAG_NUMFLAGS)
285 /* Flag does not match anything in the feature tables */
288 feat = &cpu_feature_table[feature];
291 /* This entry in the table wasn't filled out! */
294 rte_cpu_get_features(feat->leaf & 0xffff0000, 0, regs);
295 if (((regs[RTE_REG_EAX] ^ feat->leaf) & 0xffff0000) ||
296 regs[RTE_REG_EAX] < feat->leaf)
299 /* get the cpuid leaf containing the desired feature */
300 rte_cpu_get_features(feat->leaf, feat->subleaf, regs);
302 /* check if the feature is enabled */
303 return (regs[feat->reg] >> feat->bit) & 1;
310 #endif /* _RTE_CPUFLAGS_X86_64_H_ */