1 /*
2 * i386 CPUID, CPU class, definitions, models
3 *
4 * Copyright (c) 2003 Fabrice Bellard
5 *
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
10 *
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
15 *
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, see <http://www.gnu.org/licenses/>.
18 */
19
20 #include "qemu/osdep.h"
21 #include "qemu/units.h"
22 #include "qemu/cutils.h"
23 #include "qemu/qemu-print.h"
24 #include "qemu/hw-version.h"
25 #include "cpu.h"
26 #include "tcg/helper-tcg.h"
27 #include "exec/translation-block.h"
28 #include "system/hvf.h"
29 #include "hvf/hvf-i386.h"
30 #include "kvm/kvm_i386.h"
31 #include "sev.h"
32 #include "qapi/error.h"
33 #include "qemu/error-report.h"
34 #include "qapi/qapi-visit-machine.h"
35 #include "standard-headers/asm-x86/kvm_para.h"
36 #include "hw/qdev-properties.h"
37 #include "hw/i386/topology.h"
38 #include "exec/watchpoint.h"
39 #ifndef CONFIG_USER_ONLY
40 #include "confidential-guest.h"
41 #include "system/reset.h"
42 #include "qapi/qapi-commands-machine.h"
43 #include "system/address-spaces.h"
44 #include "hw/boards.h"
45 #include "hw/i386/sgx-epc.h"
46 #endif
47 #include "tcg/tcg-cpu.h"
48
49 #include "disas/capstone.h"
50 #include "cpu-internal.h"
51
52 static void x86_cpu_realizefn(DeviceState *dev, Error **errp);
53 static void x86_cpu_get_supported_cpuid(uint32_t func, uint32_t index,
54 uint32_t *eax, uint32_t *ebx,
55 uint32_t *ecx, uint32_t *edx);
56
57 /* Helpers for building CPUID[2] descriptors: */
58
59 struct CPUID2CacheDescriptorInfo {
60 enum CacheType type;
61 int level;
62 int size;
63 int line_size;
64 int associativity;
65 };
66
67 /*
68 * Known CPUID 2 cache descriptors.
69 * From Intel SDM Volume 2A, CPUID instruction
70 */
71 struct CPUID2CacheDescriptorInfo cpuid2_cache_descriptors[] = {
72 [0x06] = { .level = 1, .type = INSTRUCTION_CACHE, .size = 8 * KiB,
73 .associativity = 4, .line_size = 32, },
74 [0x08] = { .level = 1, .type = INSTRUCTION_CACHE, .size = 16 * KiB,
75 .associativity = 4, .line_size = 32, },
76 [0x09] = { .level = 1, .type = INSTRUCTION_CACHE, .size = 32 * KiB,
77 .associativity = 4, .line_size = 64, },
78 [0x0A] = { .level = 1, .type = DATA_CACHE, .size = 8 * KiB,
79 .associativity = 2, .line_size = 32, },
80 [0x0C] = { .level = 1, .type = DATA_CACHE, .size = 16 * KiB,
81 .associativity = 4, .line_size = 32, },
82 [0x0D] = { .level = 1, .type = DATA_CACHE, .size = 16 * KiB,
83 .associativity = 4, .line_size = 64, },
84 [0x0E] = { .level = 1, .type = DATA_CACHE, .size = 24 * KiB,
85 .associativity = 6, .line_size = 64, },
86 [0x1D] = { .level = 2, .type = UNIFIED_CACHE, .size = 128 * KiB,
87 .associativity = 2, .line_size = 64, },
88 [0x21] = { .level = 2, .type = UNIFIED_CACHE, .size = 256 * KiB,
89 .associativity = 8, .line_size = 64, },
90 /* lines per sector is not supported cpuid2_cache_descriptor(),
91 * so descriptors 0x22, 0x23 are not included
92 */
93 [0x24] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
94 .associativity = 16, .line_size = 64, },
95 /* lines per sector is not supported cpuid2_cache_descriptor(),
96 * so descriptors 0x25, 0x20 are not included
97 */
98 [0x2C] = { .level = 1, .type = DATA_CACHE, .size = 32 * KiB,
99 .associativity = 8, .line_size = 64, },
100 [0x30] = { .level = 1, .type = INSTRUCTION_CACHE, .size = 32 * KiB,
101 .associativity = 8, .line_size = 64, },
102 [0x41] = { .level = 2, .type = UNIFIED_CACHE, .size = 128 * KiB,
103 .associativity = 4, .line_size = 32, },
104 [0x42] = { .level = 2, .type = UNIFIED_CACHE, .size = 256 * KiB,
105 .associativity = 4, .line_size = 32, },
106 [0x43] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
107 .associativity = 4, .line_size = 32, },
108 [0x44] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
109 .associativity = 4, .line_size = 32, },
110 [0x45] = { .level = 2, .type = UNIFIED_CACHE, .size = 2 * MiB,
111 .associativity = 4, .line_size = 32, },
112 [0x46] = { .level = 3, .type = UNIFIED_CACHE, .size = 4 * MiB,
113 .associativity = 4, .line_size = 64, },
114 [0x47] = { .level = 3, .type = UNIFIED_CACHE, .size = 8 * MiB,
115 .associativity = 8, .line_size = 64, },
116 [0x48] = { .level = 2, .type = UNIFIED_CACHE, .size = 3 * MiB,
117 .associativity = 12, .line_size = 64, },
118 /* Descriptor 0x49 depends on CPU family/model, so it is not included */
119 [0x4A] = { .level = 3, .type = UNIFIED_CACHE, .size = 6 * MiB,
120 .associativity = 12, .line_size = 64, },
121 [0x4B] = { .level = 3, .type = UNIFIED_CACHE, .size = 8 * MiB,
122 .associativity = 16, .line_size = 64, },
123 [0x4C] = { .level = 3, .type = UNIFIED_CACHE, .size = 12 * MiB,
124 .associativity = 12, .line_size = 64, },
125 [0x4D] = { .level = 3, .type = UNIFIED_CACHE, .size = 16 * MiB,
126 .associativity = 16, .line_size = 64, },
127 [0x4E] = { .level = 2, .type = UNIFIED_CACHE, .size = 6 * MiB,
128 .associativity = 24, .line_size = 64, },
129 [0x60] = { .level = 1, .type = DATA_CACHE, .size = 16 * KiB,
130 .associativity = 8, .line_size = 64, },
131 [0x66] = { .level = 1, .type = DATA_CACHE, .size = 8 * KiB,
132 .associativity = 4, .line_size = 64, },
133 [0x67] = { .level = 1, .type = DATA_CACHE, .size = 16 * KiB,
134 .associativity = 4, .line_size = 64, },
135 [0x68] = { .level = 1, .type = DATA_CACHE, .size = 32 * KiB,
136 .associativity = 4, .line_size = 64, },
137 [0x78] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
138 .associativity = 4, .line_size = 64, },
139 /* lines per sector is not supported cpuid2_cache_descriptor(),
140 * so descriptors 0x79, 0x7A, 0x7B, 0x7C are not included.
141 */
142 [0x7D] = { .level = 2, .type = UNIFIED_CACHE, .size = 2 * MiB,
143 .associativity = 8, .line_size = 64, },
144 [0x7F] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
145 .associativity = 2, .line_size = 64, },
146 [0x80] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
147 .associativity = 8, .line_size = 64, },
148 [0x82] = { .level = 2, .type = UNIFIED_CACHE, .size = 256 * KiB,
149 .associativity = 8, .line_size = 32, },
150 [0x83] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
151 .associativity = 8, .line_size = 32, },
152 [0x84] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
153 .associativity = 8, .line_size = 32, },
154 [0x85] = { .level = 2, .type = UNIFIED_CACHE, .size = 2 * MiB,
155 .associativity = 8, .line_size = 32, },
156 [0x86] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
157 .associativity = 4, .line_size = 64, },
158 [0x87] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
159 .associativity = 8, .line_size = 64, },
160 [0xD0] = { .level = 3, .type = UNIFIED_CACHE, .size = 512 * KiB,
161 .associativity = 4, .line_size = 64, },
162 [0xD1] = { .level = 3, .type = UNIFIED_CACHE, .size = 1 * MiB,
163 .associativity = 4, .line_size = 64, },
164 [0xD2] = { .level = 3, .type = UNIFIED_CACHE, .size = 2 * MiB,
165 .associativity = 4, .line_size = 64, },
166 [0xD6] = { .level = 3, .type = UNIFIED_CACHE, .size = 1 * MiB,
167 .associativity = 8, .line_size = 64, },
168 [0xD7] = { .level = 3, .type = UNIFIED_CACHE, .size = 2 * MiB,
169 .associativity = 8, .line_size = 64, },
170 [0xD8] = { .level = 3, .type = UNIFIED_CACHE, .size = 4 * MiB,
171 .associativity = 8, .line_size = 64, },
172 [0xDC] = { .level = 3, .type = UNIFIED_CACHE, .size = 1.5 * MiB,
173 .associativity = 12, .line_size = 64, },
174 [0xDD] = { .level = 3, .type = UNIFIED_CACHE, .size = 3 * MiB,
175 .associativity = 12, .line_size = 64, },
176 [0xDE] = { .level = 3, .type = UNIFIED_CACHE, .size = 6 * MiB,
177 .associativity = 12, .line_size = 64, },
178 [0xE2] = { .level = 3, .type = UNIFIED_CACHE, .size = 2 * MiB,
179 .associativity = 16, .line_size = 64, },
180 [0xE3] = { .level = 3, .type = UNIFIED_CACHE, .size = 4 * MiB,
181 .associativity = 16, .line_size = 64, },
182 [0xE4] = { .level = 3, .type = UNIFIED_CACHE, .size = 8 * MiB,
183 .associativity = 16, .line_size = 64, },
184 [0xEA] = { .level = 3, .type = UNIFIED_CACHE, .size = 12 * MiB,
185 .associativity = 24, .line_size = 64, },
186 [0xEB] = { .level = 3, .type = UNIFIED_CACHE, .size = 18 * MiB,
187 .associativity = 24, .line_size = 64, },
188 [0xEC] = { .level = 3, .type = UNIFIED_CACHE, .size = 24 * MiB,
189 .associativity = 24, .line_size = 64, },
190 };
191
192 /*
193 * "CPUID leaf 2 does not report cache descriptor information,
194 * use CPUID leaf 4 to query cache parameters"
195 */
196 #define CACHE_DESCRIPTOR_UNAVAILABLE 0xFF
197
198 /*
199 * Return a CPUID 2 cache descriptor for a given cache.
200 * If no known descriptor is found, return CACHE_DESCRIPTOR_UNAVAILABLE
201 */
cpuid2_cache_descriptor(CPUCacheInfo * cache)202 static uint8_t cpuid2_cache_descriptor(CPUCacheInfo *cache)
203 {
204 int i;
205
206 assert(cache->size > 0);
207 assert(cache->level > 0);
208 assert(cache->line_size > 0);
209 assert(cache->associativity > 0);
210 for (i = 0; i < ARRAY_SIZE(cpuid2_cache_descriptors); i++) {
211 struct CPUID2CacheDescriptorInfo *d = &cpuid2_cache_descriptors[i];
212 if (d->level == cache->level && d->type == cache->type &&
213 d->size == cache->size && d->line_size == cache->line_size &&
214 d->associativity == cache->associativity) {
215 return i;
216 }
217 }
218
219 return CACHE_DESCRIPTOR_UNAVAILABLE;
220 }
221
222 /* CPUID Leaf 4 constants: */
223
224 /* EAX: */
225 #define CACHE_TYPE_D 1
226 #define CACHE_TYPE_I 2
227 #define CACHE_TYPE_UNIFIED 3
228
229 #define CACHE_LEVEL(l) (l << 5)
230
231 #define CACHE_SELF_INIT_LEVEL (1 << 8)
232
233 /* EDX: */
234 #define CACHE_NO_INVD_SHARING (1 << 0)
235 #define CACHE_INCLUSIVE (1 << 1)
236 #define CACHE_COMPLEX_IDX (1 << 2)
237
238 /* Encode CacheType for CPUID[4].EAX */
239 #define CACHE_TYPE(t) (((t) == DATA_CACHE) ? CACHE_TYPE_D : \
240 ((t) == INSTRUCTION_CACHE) ? CACHE_TYPE_I : \
241 ((t) == UNIFIED_CACHE) ? CACHE_TYPE_UNIFIED : \
242 0 /* Invalid value */)
243
max_thread_ids_for_cache(X86CPUTopoInfo * topo_info,enum CpuTopologyLevel share_level)244 static uint32_t max_thread_ids_for_cache(X86CPUTopoInfo *topo_info,
245 enum CpuTopologyLevel share_level)
246 {
247 uint32_t num_ids = 0;
248
249 switch (share_level) {
250 case CPU_TOPOLOGY_LEVEL_CORE:
251 num_ids = 1 << apicid_core_offset(topo_info);
252 break;
253 case CPU_TOPOLOGY_LEVEL_MODULE:
254 num_ids = 1 << apicid_module_offset(topo_info);
255 break;
256 case CPU_TOPOLOGY_LEVEL_DIE:
257 num_ids = 1 << apicid_die_offset(topo_info);
258 break;
259 case CPU_TOPOLOGY_LEVEL_SOCKET:
260 num_ids = 1 << apicid_pkg_offset(topo_info);
261 break;
262 default:
263 /*
264 * Currently there is no use case for THREAD, so use
265 * assert directly to facilitate debugging.
266 */
267 g_assert_not_reached();
268 }
269
270 return num_ids - 1;
271 }
272
max_core_ids_in_package(X86CPUTopoInfo * topo_info)273 static uint32_t max_core_ids_in_package(X86CPUTopoInfo *topo_info)
274 {
275 uint32_t num_cores = 1 << (apicid_pkg_offset(topo_info) -
276 apicid_core_offset(topo_info));
277 return num_cores - 1;
278 }
279
280 /* Encode cache info for CPUID[4] */
encode_cache_cpuid4(CPUCacheInfo * cache,X86CPUTopoInfo * topo_info,uint32_t * eax,uint32_t * ebx,uint32_t * ecx,uint32_t * edx)281 static void encode_cache_cpuid4(CPUCacheInfo *cache,
282 X86CPUTopoInfo *topo_info,
283 uint32_t *eax, uint32_t *ebx,
284 uint32_t *ecx, uint32_t *edx)
285 {
286 assert(cache->size == cache->line_size * cache->associativity *
287 cache->partitions * cache->sets);
288
289 *eax = CACHE_TYPE(cache->type) |
290 CACHE_LEVEL(cache->level) |
291 (cache->self_init ? CACHE_SELF_INIT_LEVEL : 0) |
292 (max_core_ids_in_package(topo_info) << 26) |
293 (max_thread_ids_for_cache(topo_info, cache->share_level) << 14);
294
295 assert(cache->line_size > 0);
296 assert(cache->partitions > 0);
297 assert(cache->associativity > 0);
298 /* We don't implement fully-associative caches */
299 assert(cache->associativity < cache->sets);
300 *ebx = (cache->line_size - 1) |
301 ((cache->partitions - 1) << 12) |
302 ((cache->associativity - 1) << 22);
303
304 assert(cache->sets > 0);
305 *ecx = cache->sets - 1;
306
307 *edx = (cache->no_invd_sharing ? CACHE_NO_INVD_SHARING : 0) |
308 (cache->inclusive ? CACHE_INCLUSIVE : 0) |
309 (cache->complex_indexing ? CACHE_COMPLEX_IDX : 0);
310 }
311
num_threads_by_topo_level(X86CPUTopoInfo * topo_info,enum CpuTopologyLevel topo_level)312 static uint32_t num_threads_by_topo_level(X86CPUTopoInfo *topo_info,
313 enum CpuTopologyLevel topo_level)
314 {
315 switch (topo_level) {
316 case CPU_TOPOLOGY_LEVEL_THREAD:
317 return 1;
318 case CPU_TOPOLOGY_LEVEL_CORE:
319 return topo_info->threads_per_core;
320 case CPU_TOPOLOGY_LEVEL_MODULE:
321 return x86_threads_per_module(topo_info);
322 case CPU_TOPOLOGY_LEVEL_DIE:
323 return x86_threads_per_die(topo_info);
324 case CPU_TOPOLOGY_LEVEL_SOCKET:
325 return x86_threads_per_pkg(topo_info);
326 default:
327 g_assert_not_reached();
328 }
329 return 0;
330 }
331
apicid_offset_by_topo_level(X86CPUTopoInfo * topo_info,enum CpuTopologyLevel topo_level)332 static uint32_t apicid_offset_by_topo_level(X86CPUTopoInfo *topo_info,
333 enum CpuTopologyLevel topo_level)
334 {
335 switch (topo_level) {
336 case CPU_TOPOLOGY_LEVEL_THREAD:
337 return 0;
338 case CPU_TOPOLOGY_LEVEL_CORE:
339 return apicid_core_offset(topo_info);
340 case CPU_TOPOLOGY_LEVEL_MODULE:
341 return apicid_module_offset(topo_info);
342 case CPU_TOPOLOGY_LEVEL_DIE:
343 return apicid_die_offset(topo_info);
344 case CPU_TOPOLOGY_LEVEL_SOCKET:
345 return apicid_pkg_offset(topo_info);
346 default:
347 g_assert_not_reached();
348 }
349 return 0;
350 }
351
cpuid1f_topo_type(enum CpuTopologyLevel topo_level)352 static uint32_t cpuid1f_topo_type(enum CpuTopologyLevel topo_level)
353 {
354 switch (topo_level) {
355 case CPU_TOPOLOGY_LEVEL_INVALID:
356 return CPUID_1F_ECX_TOPO_LEVEL_INVALID;
357 case CPU_TOPOLOGY_LEVEL_THREAD:
358 return CPUID_1F_ECX_TOPO_LEVEL_SMT;
359 case CPU_TOPOLOGY_LEVEL_CORE:
360 return CPUID_1F_ECX_TOPO_LEVEL_CORE;
361 case CPU_TOPOLOGY_LEVEL_MODULE:
362 return CPUID_1F_ECX_TOPO_LEVEL_MODULE;
363 case CPU_TOPOLOGY_LEVEL_DIE:
364 return CPUID_1F_ECX_TOPO_LEVEL_DIE;
365 default:
366 /* Other types are not supported in QEMU. */
367 g_assert_not_reached();
368 }
369 return 0;
370 }
371
encode_topo_cpuid1f(CPUX86State * env,uint32_t count,X86CPUTopoInfo * topo_info,uint32_t * eax,uint32_t * ebx,uint32_t * ecx,uint32_t * edx)372 static void encode_topo_cpuid1f(CPUX86State *env, uint32_t count,
373 X86CPUTopoInfo *topo_info,
374 uint32_t *eax, uint32_t *ebx,
375 uint32_t *ecx, uint32_t *edx)
376 {
377 X86CPU *cpu = env_archcpu(env);
378 unsigned long level, base_level, next_level;
379 uint32_t num_threads_next_level, offset_next_level;
380
381 assert(count <= CPU_TOPOLOGY_LEVEL_SOCKET);
382
383 /*
384 * Find the No.(count + 1) topology level in avail_cpu_topo bitmap.
385 * The search starts from bit 0 (CPU_TOPOLOGY_LEVEL_THREAD).
386 */
387 level = CPU_TOPOLOGY_LEVEL_THREAD;
388 base_level = level;
389 for (int i = 0; i <= count; i++) {
390 level = find_next_bit(env->avail_cpu_topo,
391 CPU_TOPOLOGY_LEVEL_SOCKET,
392 base_level);
393
394 /*
395 * CPUID[0x1f] doesn't explicitly encode the package level,
396 * and it just encodes the invalid level (all fields are 0)
397 * into the last subleaf of 0x1f.
398 */
399 if (level == CPU_TOPOLOGY_LEVEL_SOCKET) {
400 level = CPU_TOPOLOGY_LEVEL_INVALID;
401 break;
402 }
403 /* Search the next level. */
404 base_level = level + 1;
405 }
406
407 if (level == CPU_TOPOLOGY_LEVEL_INVALID) {
408 num_threads_next_level = 0;
409 offset_next_level = 0;
410 } else {
411 next_level = find_next_bit(env->avail_cpu_topo,
412 CPU_TOPOLOGY_LEVEL_SOCKET,
413 level + 1);
414 num_threads_next_level = num_threads_by_topo_level(topo_info,
415 next_level);
416 offset_next_level = apicid_offset_by_topo_level(topo_info,
417 next_level);
418 }
419
420 *eax = offset_next_level;
421 /* The count (bits 15-00) doesn't need to be reliable. */
422 *ebx = num_threads_next_level & 0xffff;
423 *ecx = (count & 0xff) | (cpuid1f_topo_type(level) << 8);
424 *edx = cpu->apic_id;
425
426 assert(!(*eax & ~0x1f));
427 }
428
429 /* Encode cache info for CPUID[0x80000005].ECX or CPUID[0x80000005].EDX */
encode_cache_cpuid80000005(CPUCacheInfo * cache)430 static uint32_t encode_cache_cpuid80000005(CPUCacheInfo *cache)
431 {
432 assert(cache->size % 1024 == 0);
433 assert(cache->lines_per_tag > 0);
434 assert(cache->associativity > 0);
435 assert(cache->line_size > 0);
436 return ((cache->size / 1024) << 24) | (cache->associativity << 16) |
437 (cache->lines_per_tag << 8) | (cache->line_size);
438 }
439
440 #define ASSOC_FULL 0xFF
441
442 /* AMD associativity encoding used on CPUID Leaf 0x80000006: */
443 #define AMD_ENC_ASSOC(a) (a <= 1 ? a : \
444 a == 2 ? 0x2 : \
445 a == 4 ? 0x4 : \
446 a == 8 ? 0x6 : \
447 a == 16 ? 0x8 : \
448 a == 32 ? 0xA : \
449 a == 48 ? 0xB : \
450 a == 64 ? 0xC : \
451 a == 96 ? 0xD : \
452 a == 128 ? 0xE : \
453 a == ASSOC_FULL ? 0xF : \
454 0 /* invalid value */)
455
456 /*
457 * Encode cache info for CPUID[0x80000006].ECX and CPUID[0x80000006].EDX
458 * @l3 can be NULL.
459 */
encode_cache_cpuid80000006(CPUCacheInfo * l2,CPUCacheInfo * l3,uint32_t * ecx,uint32_t * edx)460 static void encode_cache_cpuid80000006(CPUCacheInfo *l2,
461 CPUCacheInfo *l3,
462 uint32_t *ecx, uint32_t *edx)
463 {
464 assert(l2->size % 1024 == 0);
465 assert(l2->associativity > 0);
466 assert(l2->lines_per_tag > 0);
467 assert(l2->line_size > 0);
468 *ecx = ((l2->size / 1024) << 16) |
469 (AMD_ENC_ASSOC(l2->associativity) << 12) |
470 (l2->lines_per_tag << 8) | (l2->line_size);
471
472 if (l3) {
473 assert(l3->size % (512 * 1024) == 0);
474 assert(l3->associativity > 0);
475 assert(l3->lines_per_tag > 0);
476 assert(l3->line_size > 0);
477 *edx = ((l3->size / (512 * 1024)) << 18) |
478 (AMD_ENC_ASSOC(l3->associativity) << 12) |
479 (l3->lines_per_tag << 8) | (l3->line_size);
480 } else {
481 *edx = 0;
482 }
483 }
484
485 /* Encode cache info for CPUID[8000001D] */
encode_cache_cpuid8000001d(CPUCacheInfo * cache,X86CPUTopoInfo * topo_info,uint32_t * eax,uint32_t * ebx,uint32_t * ecx,uint32_t * edx)486 static void encode_cache_cpuid8000001d(CPUCacheInfo *cache,
487 X86CPUTopoInfo *topo_info,
488 uint32_t *eax, uint32_t *ebx,
489 uint32_t *ecx, uint32_t *edx)
490 {
491 assert(cache->size == cache->line_size * cache->associativity *
492 cache->partitions * cache->sets);
493
494 *eax = CACHE_TYPE(cache->type) | CACHE_LEVEL(cache->level) |
495 (cache->self_init ? CACHE_SELF_INIT_LEVEL : 0);
496 *eax |= max_thread_ids_for_cache(topo_info, cache->share_level) << 14;
497
498 assert(cache->line_size > 0);
499 assert(cache->partitions > 0);
500 assert(cache->associativity > 0);
501 /* We don't implement fully-associative caches */
502 assert(cache->associativity < cache->sets);
503 *ebx = (cache->line_size - 1) |
504 ((cache->partitions - 1) << 12) |
505 ((cache->associativity - 1) << 22);
506
507 assert(cache->sets > 0);
508 *ecx = cache->sets - 1;
509
510 *edx = (cache->no_invd_sharing ? CACHE_NO_INVD_SHARING : 0) |
511 (cache->inclusive ? CACHE_INCLUSIVE : 0) |
512 (cache->complex_indexing ? CACHE_COMPLEX_IDX : 0);
513 }
514
515 /* Encode cache info for CPUID[8000001E] */
encode_topo_cpuid8000001e(X86CPU * cpu,X86CPUTopoInfo * topo_info,uint32_t * eax,uint32_t * ebx,uint32_t * ecx,uint32_t * edx)516 static void encode_topo_cpuid8000001e(X86CPU *cpu, X86CPUTopoInfo *topo_info,
517 uint32_t *eax, uint32_t *ebx,
518 uint32_t *ecx, uint32_t *edx)
519 {
520 X86CPUTopoIDs topo_ids;
521
522 x86_topo_ids_from_apicid(cpu->apic_id, topo_info, &topo_ids);
523
524 *eax = cpu->apic_id;
525
526 /*
527 * CPUID_Fn8000001E_EBX [Core Identifiers] (CoreId)
528 * Read-only. Reset: 0000_XXXXh.
529 * See Core::X86::Cpuid::ExtApicId.
530 * Core::X86::Cpuid::CoreId_lthree[1:0]_core[3:0]_thread[1:0];
531 * Bits Description
532 * 31:16 Reserved.
533 * 15:8 ThreadsPerCore: threads per core. Read-only. Reset: XXh.
534 * The number of threads per core is ThreadsPerCore+1.
535 * 7:0 CoreId: core ID. Read-only. Reset: XXh.
536 *
537 * NOTE: CoreId is already part of apic_id. Just use it. We can
538 * use all the 8 bits to represent the core_id here.
539 */
540 *ebx = ((topo_info->threads_per_core - 1) << 8) | (topo_ids.core_id & 0xFF);
541
542 /*
543 * CPUID_Fn8000001E_ECX [Node Identifiers] (NodeId)
544 * Read-only. Reset: 0000_0XXXh.
545 * Core::X86::Cpuid::NodeId_lthree[1:0]_core[3:0]_thread[1:0];
546 * Bits Description
547 * 31:11 Reserved.
548 * 10:8 NodesPerProcessor: Node per processor. Read-only. Reset: XXXb.
549 * ValidValues:
550 * Value Description
551 * 0h 1 node per processor.
552 * 7h-1h Reserved.
553 * 7:0 NodeId: Node ID. Read-only. Reset: XXh.
554 *
555 * NOTE: Hardware reserves 3 bits for number of nodes per processor.
556 * But users can create more nodes than the actual hardware can
557 * support. To genaralize we can use all the upper 8 bits for nodes.
558 * NodeId is combination of node and socket_id which is already decoded
559 * in apic_id. Just use it by shifting.
560 */
561 if (cpu->legacy_multi_node) {
562 *ecx = ((topo_info->dies_per_pkg - 1) << 8) |
563 ((cpu->apic_id >> apicid_die_offset(topo_info)) & 0xFF);
564 } else {
565 *ecx = (cpu->apic_id >> apicid_pkg_offset(topo_info)) & 0xFF;
566 }
567
568 *edx = 0;
569 }
570
571 /*
572 * Definitions of the hardcoded cache entries we expose:
573 * These are legacy cache values. If there is a need to change any
574 * of these values please use builtin_x86_defs
575 */
576
577 /* L1 data cache: */
578 static CPUCacheInfo legacy_l1d_cache = {
579 .type = DATA_CACHE,
580 .level = 1,
581 .size = 32 * KiB,
582 .self_init = 1,
583 .line_size = 64,
584 .associativity = 8,
585 .sets = 64,
586 .partitions = 1,
587 .no_invd_sharing = true,
588 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
589 };
590
591 /*FIXME: CPUID leaf 0x80000005 is inconsistent with leaves 2 & 4 */
592 static CPUCacheInfo legacy_l1d_cache_amd = {
593 .type = DATA_CACHE,
594 .level = 1,
595 .size = 64 * KiB,
596 .self_init = 1,
597 .line_size = 64,
598 .associativity = 2,
599 .sets = 512,
600 .partitions = 1,
601 .lines_per_tag = 1,
602 .no_invd_sharing = true,
603 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
604 };
605
606 /* L1 instruction cache: */
607 static CPUCacheInfo legacy_l1i_cache = {
608 .type = INSTRUCTION_CACHE,
609 .level = 1,
610 .size = 32 * KiB,
611 .self_init = 1,
612 .line_size = 64,
613 .associativity = 8,
614 .sets = 64,
615 .partitions = 1,
616 .no_invd_sharing = true,
617 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
618 };
619
620 /*FIXME: CPUID leaf 0x80000005 is inconsistent with leaves 2 & 4 */
621 static CPUCacheInfo legacy_l1i_cache_amd = {
622 .type = INSTRUCTION_CACHE,
623 .level = 1,
624 .size = 64 * KiB,
625 .self_init = 1,
626 .line_size = 64,
627 .associativity = 2,
628 .sets = 512,
629 .partitions = 1,
630 .lines_per_tag = 1,
631 .no_invd_sharing = true,
632 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
633 };
634
635 /* Level 2 unified cache: */
636 static CPUCacheInfo legacy_l2_cache = {
637 .type = UNIFIED_CACHE,
638 .level = 2,
639 .size = 4 * MiB,
640 .self_init = 1,
641 .line_size = 64,
642 .associativity = 16,
643 .sets = 4096,
644 .partitions = 1,
645 .no_invd_sharing = true,
646 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
647 };
648
649 /*FIXME: CPUID leaf 2 descriptor is inconsistent with CPUID leaf 4 */
650 static CPUCacheInfo legacy_l2_cache_cpuid2 = {
651 .type = UNIFIED_CACHE,
652 .level = 2,
653 .size = 2 * MiB,
654 .line_size = 64,
655 .associativity = 8,
656 .share_level = CPU_TOPOLOGY_LEVEL_INVALID,
657 };
658
659
660 /*FIXME: CPUID leaf 0x80000006 is inconsistent with leaves 2 & 4 */
661 static CPUCacheInfo legacy_l2_cache_amd = {
662 .type = UNIFIED_CACHE,
663 .level = 2,
664 .size = 512 * KiB,
665 .line_size = 64,
666 .lines_per_tag = 1,
667 .associativity = 16,
668 .sets = 512,
669 .partitions = 1,
670 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
671 };
672
673 /* Level 3 unified cache: */
674 static CPUCacheInfo legacy_l3_cache = {
675 .type = UNIFIED_CACHE,
676 .level = 3,
677 .size = 16 * MiB,
678 .line_size = 64,
679 .associativity = 16,
680 .sets = 16384,
681 .partitions = 1,
682 .lines_per_tag = 1,
683 .self_init = true,
684 .inclusive = true,
685 .complex_indexing = true,
686 .share_level = CPU_TOPOLOGY_LEVEL_DIE,
687 };
688
689 /* TLB definitions: */
690
691 #define L1_DTLB_2M_ASSOC 1
692 #define L1_DTLB_2M_ENTRIES 255
693 #define L1_DTLB_4K_ASSOC 1
694 #define L1_DTLB_4K_ENTRIES 255
695
696 #define L1_ITLB_2M_ASSOC 1
697 #define L1_ITLB_2M_ENTRIES 255
698 #define L1_ITLB_4K_ASSOC 1
699 #define L1_ITLB_4K_ENTRIES 255
700
701 #define L2_DTLB_2M_ASSOC 0 /* disabled */
702 #define L2_DTLB_2M_ENTRIES 0 /* disabled */
703 #define L2_DTLB_4K_ASSOC 4
704 #define L2_DTLB_4K_ENTRIES 512
705
706 #define L2_ITLB_2M_ASSOC 0 /* disabled */
707 #define L2_ITLB_2M_ENTRIES 0 /* disabled */
708 #define L2_ITLB_4K_ASSOC 4
709 #define L2_ITLB_4K_ENTRIES 512
710
711 /* CPUID Leaf 0x14 constants: */
712 #define INTEL_PT_MAX_SUBLEAF 0x1
713 /*
714 * bit[00]: IA32_RTIT_CTL.CR3 filter can be set to 1 and IA32_RTIT_CR3_MATCH
715 * MSR can be accessed;
716 * bit[01]: Support Configurable PSB and Cycle-Accurate Mode;
717 * bit[02]: Support IP Filtering, TraceStop filtering, and preservation
718 * of Intel PT MSRs across warm reset;
719 * bit[03]: Support MTC timing packet and suppression of COFI-based packets;
720 */
721 #define INTEL_PT_MINIMAL_EBX 0xf
722 /*
723 * bit[00]: Tracing can be enabled with IA32_RTIT_CTL.ToPA = 1 and
724 * IA32_RTIT_OUTPUT_BASE and IA32_RTIT_OUTPUT_MASK_PTRS MSRs can be
725 * accessed;
726 * bit[01]: ToPA tables can hold any number of output entries, up to the
727 * maximum allowed by the MaskOrTableOffset field of
728 * IA32_RTIT_OUTPUT_MASK_PTRS;
729 * bit[02]: Support Single-Range Output scheme;
730 */
731 #define INTEL_PT_MINIMAL_ECX 0x7
732 /* generated packets which contain IP payloads have LIP values */
733 #define INTEL_PT_IP_LIP (1 << 31)
734 #define INTEL_PT_ADDR_RANGES_NUM 0x2 /* Number of configurable address ranges */
735 #define INTEL_PT_ADDR_RANGES_NUM_MASK 0x3
736 #define INTEL_PT_MTC_BITMAP (0x0249 << 16) /* Support ART(0,3,6,9) */
737 #define INTEL_PT_CYCLE_BITMAP 0x1fff /* Support 0,2^(0~11) */
738 #define INTEL_PT_PSB_BITMAP (0x003f << 16) /* Support 2K,4K,8K,16K,32K,64K */
739
740 /* CPUID Leaf 0x1D constants: */
741 #define INTEL_AMX_TILE_MAX_SUBLEAF 0x1
742 #define INTEL_AMX_TOTAL_TILE_BYTES 0x2000
743 #define INTEL_AMX_BYTES_PER_TILE 0x400
744 #define INTEL_AMX_BYTES_PER_ROW 0x40
745 #define INTEL_AMX_TILE_MAX_NAMES 0x8
746 #define INTEL_AMX_TILE_MAX_ROWS 0x10
747
748 /* CPUID Leaf 0x1E constants: */
749 #define INTEL_AMX_TMUL_MAX_K 0x10
750 #define INTEL_AMX_TMUL_MAX_N 0x40
751
x86_cpu_vendor_words2str(char * dst,uint32_t vendor1,uint32_t vendor2,uint32_t vendor3)752 void x86_cpu_vendor_words2str(char *dst, uint32_t vendor1,
753 uint32_t vendor2, uint32_t vendor3)
754 {
755 int i;
756 for (i = 0; i < 4; i++) {
757 dst[i] = vendor1 >> (8 * i);
758 dst[i + 4] = vendor2 >> (8 * i);
759 dst[i + 8] = vendor3 >> (8 * i);
760 }
761 dst[CPUID_VENDOR_SZ] = '\0';
762 }
763
764 #define I486_FEATURES (CPUID_FP87 | CPUID_VME | CPUID_PSE)
765 #define PENTIUM_FEATURES (I486_FEATURES | CPUID_DE | CPUID_TSC | \
766 CPUID_MSR | CPUID_MCE | CPUID_CX8 | CPUID_MMX | CPUID_APIC)
767 #define PENTIUM2_FEATURES (PENTIUM_FEATURES | CPUID_PAE | CPUID_SEP | \
768 CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV | CPUID_PAT | \
769 CPUID_PSE36 | CPUID_FXSR)
770 #define PENTIUM3_FEATURES (PENTIUM2_FEATURES | CPUID_SSE)
771 #define PPRO_FEATURES (CPUID_FP87 | CPUID_DE | CPUID_PSE | CPUID_TSC | \
772 CPUID_MSR | CPUID_MCE | CPUID_CX8 | CPUID_PGE | CPUID_CMOV | \
773 CPUID_PAT | CPUID_FXSR | CPUID_MMX | CPUID_SSE | CPUID_SSE2 | \
774 CPUID_PAE | CPUID_SEP | CPUID_APIC)
775
776 #define TCG_FEATURES (CPUID_FP87 | CPUID_PSE | CPUID_TSC | CPUID_MSR | \
777 CPUID_PAE | CPUID_MCE | CPUID_CX8 | CPUID_APIC | CPUID_SEP | \
778 CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV | CPUID_PAT | \
779 CPUID_PSE36 | CPUID_CLFLUSH | CPUID_ACPI | CPUID_MMX | \
780 CPUID_FXSR | CPUID_SSE | CPUID_SSE2 | CPUID_SS | CPUID_DE | \
781 CPUID_HT)
782 /* partly implemented:
783 CPUID_MTRR, CPUID_MCA, CPUID_CLFLUSH (needed for Win64) */
784 /* missing:
785 CPUID_VME, CPUID_DTS, CPUID_SS, CPUID_TM, CPUID_PBE */
786
787 /*
788 * Kernel-only features that can be shown to usermode programs even if
789 * they aren't actually supported by TCG, because qemu-user only runs
790 * in CPL=3; remove them if they are ever implemented for system emulation.
791 */
792 #if defined CONFIG_USER_ONLY
793 #define CPUID_EXT_KERNEL_FEATURES \
794 (CPUID_EXT_PCID | CPUID_EXT_TSC_DEADLINE_TIMER)
795 #else
796 #define CPUID_EXT_KERNEL_FEATURES 0
797 #endif
798 #define TCG_EXT_FEATURES (CPUID_EXT_SSE3 | CPUID_EXT_PCLMULQDQ | \
799 CPUID_EXT_MONITOR | CPUID_EXT_SSSE3 | CPUID_EXT_CX16 | \
800 CPUID_EXT_SSE41 | CPUID_EXT_SSE42 | CPUID_EXT_POPCNT | \
801 CPUID_EXT_XSAVE | /* CPUID_EXT_OSXSAVE is dynamic */ \
802 CPUID_EXT_MOVBE | CPUID_EXT_AES | CPUID_EXT_HYPERVISOR | \
803 CPUID_EXT_RDRAND | CPUID_EXT_AVX | CPUID_EXT_F16C | \
804 CPUID_EXT_FMA | CPUID_EXT_X2APIC | CPUID_EXT_KERNEL_FEATURES)
805 /* missing:
806 CPUID_EXT_DTES64, CPUID_EXT_DSCPL, CPUID_EXT_VMX, CPUID_EXT_SMX,
807 CPUID_EXT_EST, CPUID_EXT_TM2, CPUID_EXT_CID,
808 CPUID_EXT_XTPR, CPUID_EXT_PDCM, CPUID_EXT_PCID, CPUID_EXT_DCA,
809 CPUID_EXT_TSC_DEADLINE_TIMER
810 */
811
812 #ifdef TARGET_X86_64
813 #define TCG_EXT2_X86_64_FEATURES CPUID_EXT2_LM
814 #else
815 #define TCG_EXT2_X86_64_FEATURES 0
816 #endif
817
818 /*
819 * CPUID_*_KERNEL_FEATURES denotes bits and features that are not usable
820 * in usermode or by 32-bit programs. Those are added to supported
821 * TCG features unconditionally in user-mode emulation mode. This may
822 * indeed seem strange or incorrect, but it works because code running
823 * under usermode emulation cannot access them.
824 *
825 * Even for long mode, qemu-i386 is not running "a userspace program on a
826 * 32-bit CPU"; it's running "a userspace program with a 32-bit code segment"
827 * and therefore using the 32-bit ABI; the CPU itself might be 64-bit
828 * but again the difference is only visible in kernel mode.
829 */
830 #if defined CONFIG_LINUX_USER
831 #define CPUID_EXT2_KERNEL_FEATURES (CPUID_EXT2_LM | CPUID_EXT2_FFXSR)
832 #elif defined CONFIG_USER_ONLY
833 /* FIXME: Long mode not yet supported for i386 bsd-user */
834 #define CPUID_EXT2_KERNEL_FEATURES CPUID_EXT2_FFXSR
835 #else
836 #define CPUID_EXT2_KERNEL_FEATURES 0
837 #endif
838
839 #define TCG_EXT2_FEATURES ((TCG_FEATURES & CPUID_EXT2_AMD_ALIASES) | \
840 CPUID_EXT2_NX | CPUID_EXT2_MMXEXT | CPUID_EXT2_RDTSCP | \
841 CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT | CPUID_EXT2_PDPE1GB | \
842 CPUID_EXT2_SYSCALL | TCG_EXT2_X86_64_FEATURES | \
843 CPUID_EXT2_KERNEL_FEATURES)
844
845 #if defined CONFIG_USER_ONLY
846 #define CPUID_EXT3_KERNEL_FEATURES CPUID_EXT3_OSVW
847 #else
848 #define CPUID_EXT3_KERNEL_FEATURES 0
849 #endif
850
851 #define TCG_EXT3_FEATURES (CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM | \
852 CPUID_EXT3_CR8LEG | CPUID_EXT3_ABM | CPUID_EXT3_SSE4A | \
853 CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_KERNEL_FEATURES | \
854 CPUID_EXT3_CMP_LEG)
855
856 #define TCG_EXT4_FEATURES 0
857
858 #if defined CONFIG_USER_ONLY
859 #define CPUID_SVM_KERNEL_FEATURES (CPUID_SVM_NRIPSAVE | CPUID_SVM_VNMI)
860 #else
861 #define CPUID_SVM_KERNEL_FEATURES 0
862 #endif
863 #define TCG_SVM_FEATURES (CPUID_SVM_NPT | CPUID_SVM_VGIF | \
864 CPUID_SVM_SVME_ADDR_CHK | CPUID_SVM_KERNEL_FEATURES)
865
866 #define TCG_KVM_FEATURES 0
867
868 #if defined CONFIG_USER_ONLY
869 #define CPUID_7_0_EBX_KERNEL_FEATURES CPUID_7_0_EBX_INVPCID
870 #else
871 #define CPUID_7_0_EBX_KERNEL_FEATURES 0
872 #endif
873 #define TCG_7_0_EBX_FEATURES (CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_SMAP | \
874 CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ADX | \
875 CPUID_7_0_EBX_CLFLUSHOPT | \
876 CPUID_7_0_EBX_CLWB | CPUID_7_0_EBX_MPX | CPUID_7_0_EBX_FSGSBASE | \
877 CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_RDSEED | \
878 CPUID_7_0_EBX_SHA_NI | CPUID_7_0_EBX_KERNEL_FEATURES)
879 /* missing:
880 CPUID_7_0_EBX_HLE
881 CPUID_7_0_EBX_INVPCID, CPUID_7_0_EBX_RTM */
882
883 #if !defined CONFIG_USER_ONLY || defined CONFIG_LINUX
884 #define TCG_7_0_ECX_RDPID CPUID_7_0_ECX_RDPID
885 #else
886 #define TCG_7_0_ECX_RDPID 0
887 #endif
888 #define TCG_7_0_ECX_FEATURES (CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_PKU | \
889 /* CPUID_7_0_ECX_OSPKE is dynamic */ \
890 CPUID_7_0_ECX_LA57 | CPUID_7_0_ECX_PKS | CPUID_7_0_ECX_VAES | \
891 TCG_7_0_ECX_RDPID)
892
893 #if defined CONFIG_USER_ONLY
894 #define CPUID_7_0_EDX_KERNEL_FEATURES (CPUID_7_0_EDX_SPEC_CTRL | \
895 CPUID_7_0_EDX_ARCH_CAPABILITIES | CPUID_7_0_EDX_SPEC_CTRL_SSBD)
896 #else
897 #define CPUID_7_0_EDX_KERNEL_FEATURES 0
898 #endif
899 #define TCG_7_0_EDX_FEATURES (CPUID_7_0_EDX_FSRM | CPUID_7_0_EDX_KERNEL_FEATURES)
900
901 #define TCG_7_1_EAX_FEATURES (CPUID_7_1_EAX_FZRM | CPUID_7_1_EAX_FSRS | \
902 CPUID_7_1_EAX_FSRC | CPUID_7_1_EAX_CMPCCXADD)
903 #define TCG_7_1_ECX_FEATURES 0
904 #define TCG_7_1_EDX_FEATURES 0
905 #define TCG_7_2_EDX_FEATURES 0
906 #define TCG_APM_FEATURES 0
907 #define TCG_6_EAX_FEATURES CPUID_6_EAX_ARAT
908 #define TCG_XSAVE_FEATURES (CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XGETBV1)
909 /* missing:
910 CPUID_XSAVE_XSAVEC, CPUID_XSAVE_XSAVES */
911 #define TCG_14_0_ECX_FEATURES 0
912 #define TCG_SGX_12_0_EAX_FEATURES 0
913 #define TCG_SGX_12_0_EBX_FEATURES 0
914 #define TCG_SGX_12_1_EAX_FEATURES 0
915 #define TCG_24_0_EBX_FEATURES 0
916
917 #if defined CONFIG_USER_ONLY
918 #define CPUID_8000_0008_EBX_KERNEL_FEATURES (CPUID_8000_0008_EBX_IBPB | \
919 CPUID_8000_0008_EBX_IBRS | CPUID_8000_0008_EBX_STIBP | \
920 CPUID_8000_0008_EBX_STIBP_ALWAYS_ON | CPUID_8000_0008_EBX_AMD_SSBD | \
921 CPUID_8000_0008_EBX_AMD_PSFD)
922 #else
923 #define CPUID_8000_0008_EBX_KERNEL_FEATURES 0
924 #endif
925
926 #define TCG_8000_0008_EBX (CPUID_8000_0008_EBX_XSAVEERPTR | \
927 CPUID_8000_0008_EBX_WBNOINVD | CPUID_8000_0008_EBX_KERNEL_FEATURES)
928
929 #if defined CONFIG_USER_ONLY
930 #define CPUID_8000_0021_EAX_KERNEL_FEATURES CPUID_8000_0021_EAX_AUTO_IBRS
931 #else
932 #define CPUID_8000_0021_EAX_KERNEL_FEATURES 0
933 #endif
934
935 #define TCG_8000_0021_EAX_FEATURES ( \
936 CPUID_8000_0021_EAX_NO_NESTED_DATA_BP | \
937 CPUID_8000_0021_EAX_NULL_SEL_CLR_BASE | \
938 CPUID_8000_0021_EAX_KERNEL_FEATURES)
939
940 FeatureWordInfo feature_word_info[FEATURE_WORDS] = {
941 [FEAT_1_EDX] = {
942 .type = CPUID_FEATURE_WORD,
943 .feat_names = {
944 "fpu", "vme", "de", "pse",
945 "tsc", "msr", "pae", "mce",
946 "cx8", "apic", NULL, "sep",
947 "mtrr", "pge", "mca", "cmov",
948 "pat", "pse36", "pn" /* Intel psn */, "clflush" /* Intel clfsh */,
949 NULL, "ds" /* Intel dts */, "acpi", "mmx",
950 "fxsr", "sse", "sse2", "ss",
951 "ht" /* Intel htt */, "tm", "ia64", "pbe",
952 },
953 .cpuid = {.eax = 1, .reg = R_EDX, },
954 .tcg_features = TCG_FEATURES,
955 .no_autoenable_flags = CPUID_HT,
956 },
957 [FEAT_1_ECX] = {
958 .type = CPUID_FEATURE_WORD,
959 .feat_names = {
960 "pni" /* Intel,AMD sse3 */, "pclmulqdq", "dtes64", "monitor",
961 "ds-cpl", "vmx", "smx", "est",
962 "tm2", "ssse3", "cid", NULL,
963 "fma", "cx16", "xtpr", "pdcm",
964 NULL, "pcid", "dca", "sse4.1",
965 "sse4.2", "x2apic", "movbe", "popcnt",
966 "tsc-deadline", "aes", "xsave", NULL /* osxsave */,
967 "avx", "f16c", "rdrand", "hypervisor",
968 },
969 .cpuid = { .eax = 1, .reg = R_ECX, },
970 .tcg_features = TCG_EXT_FEATURES,
971 },
972 /* Feature names that are already defined on feature_name[] but
973 * are set on CPUID[8000_0001].EDX on AMD CPUs don't have their
974 * names on feat_names below. They are copied automatically
975 * to features[FEAT_8000_0001_EDX] if and only if CPU vendor is AMD.
976 */
977 [FEAT_8000_0001_EDX] = {
978 .type = CPUID_FEATURE_WORD,
979 .feat_names = {
980 NULL /* fpu */, NULL /* vme */, NULL /* de */, NULL /* pse */,
981 NULL /* tsc */, NULL /* msr */, NULL /* pae */, NULL /* mce */,
982 NULL /* cx8 */, NULL /* apic */, NULL, "syscall",
983 NULL /* mtrr */, NULL /* pge */, NULL /* mca */, NULL /* cmov */,
984 NULL /* pat */, NULL /* pse36 */, NULL, NULL /* Linux mp */,
985 "nx", NULL, "mmxext", NULL /* mmx */,
986 NULL /* fxsr */, "fxsr-opt", "pdpe1gb", "rdtscp",
987 NULL, "lm", "3dnowext", "3dnow",
988 },
989 .cpuid = { .eax = 0x80000001, .reg = R_EDX, },
990 .tcg_features = TCG_EXT2_FEATURES,
991 },
992 [FEAT_8000_0001_ECX] = {
993 .type = CPUID_FEATURE_WORD,
994 .feat_names = {
995 "lahf-lm", "cmp-legacy", "svm", "extapic",
996 "cr8legacy", "abm", "sse4a", "misalignsse",
997 "3dnowprefetch", "osvw", "ibs", "xop",
998 "skinit", "wdt", NULL, "lwp",
999 "fma4", "tce", NULL, "nodeid-msr",
1000 NULL, "tbm", "topoext", "perfctr-core",
1001 "perfctr-nb", NULL, NULL, NULL,
1002 NULL, NULL, NULL, NULL,
1003 },
1004 .cpuid = { .eax = 0x80000001, .reg = R_ECX, },
1005 .tcg_features = TCG_EXT3_FEATURES,
1006 /*
1007 * TOPOEXT is always allowed but can't be enabled blindly by
1008 * "-cpu host", as it requires consistent cache topology info
1009 * to be provided so it doesn't confuse guests.
1010 */
1011 .no_autoenable_flags = CPUID_EXT3_TOPOEXT,
1012 },
1013 [FEAT_C000_0001_EDX] = {
1014 .type = CPUID_FEATURE_WORD,
1015 .feat_names = {
1016 NULL, NULL, "xstore", "xstore-en",
1017 NULL, NULL, "xcrypt", "xcrypt-en",
1018 "ace2", "ace2-en", "phe", "phe-en",
1019 "pmm", "pmm-en", NULL, NULL,
1020 NULL, NULL, NULL, NULL,
1021 NULL, NULL, NULL, NULL,
1022 NULL, NULL, NULL, NULL,
1023 NULL, NULL, NULL, NULL,
1024 },
1025 .cpuid = { .eax = 0xC0000001, .reg = R_EDX, },
1026 .tcg_features = TCG_EXT4_FEATURES,
1027 },
1028 [FEAT_KVM] = {
1029 .type = CPUID_FEATURE_WORD,
1030 .feat_names = {
1031 "kvmclock", "kvm-nopiodelay", "kvm-mmu", "kvmclock",
1032 "kvm-asyncpf", "kvm-steal-time", "kvm-pv-eoi", "kvm-pv-unhalt",
1033 NULL, "kvm-pv-tlb-flush", "kvm-asyncpf-vmexit", "kvm-pv-ipi",
1034 "kvm-poll-control", "kvm-pv-sched-yield", "kvm-asyncpf-int", "kvm-msi-ext-dest-id",
1035 NULL, NULL, NULL, NULL,
1036 NULL, NULL, NULL, NULL,
1037 "kvmclock-stable-bit", NULL, NULL, NULL,
1038 NULL, NULL, NULL, NULL,
1039 },
1040 .cpuid = { .eax = KVM_CPUID_FEATURES, .reg = R_EAX, },
1041 .tcg_features = TCG_KVM_FEATURES,
1042 },
1043 [FEAT_KVM_HINTS] = {
1044 .type = CPUID_FEATURE_WORD,
1045 .feat_names = {
1046 "kvm-hint-dedicated", NULL, NULL, NULL,
1047 NULL, NULL, NULL, NULL,
1048 NULL, NULL, NULL, NULL,
1049 NULL, NULL, NULL, NULL,
1050 NULL, NULL, NULL, NULL,
1051 NULL, NULL, NULL, NULL,
1052 NULL, NULL, NULL, NULL,
1053 NULL, NULL, NULL, NULL,
1054 },
1055 .cpuid = { .eax = KVM_CPUID_FEATURES, .reg = R_EDX, },
1056 .tcg_features = TCG_KVM_FEATURES,
1057 /*
1058 * KVM hints aren't auto-enabled by -cpu host, they need to be
1059 * explicitly enabled in the command-line.
1060 */
1061 .no_autoenable_flags = ~0U,
1062 },
1063 [FEAT_SVM] = {
1064 .type = CPUID_FEATURE_WORD,
1065 .feat_names = {
1066 "npt", "lbrv", "svm-lock", "nrip-save",
1067 "tsc-scale", "vmcb-clean", "flushbyasid", "decodeassists",
1068 NULL, NULL, "pause-filter", NULL,
1069 "pfthreshold", "avic", NULL, "v-vmsave-vmload",
1070 "vgif", NULL, NULL, NULL,
1071 NULL, NULL, NULL, NULL,
1072 NULL, "vnmi", NULL, NULL,
1073 "svme-addr-chk", NULL, NULL, NULL,
1074 },
1075 .cpuid = { .eax = 0x8000000A, .reg = R_EDX, },
1076 .tcg_features = TCG_SVM_FEATURES,
1077 },
1078 [FEAT_7_0_EBX] = {
1079 .type = CPUID_FEATURE_WORD,
1080 .feat_names = {
1081 "fsgsbase", "tsc-adjust", "sgx", "bmi1",
1082 "hle", "avx2", "fdp-excptn-only", "smep",
1083 "bmi2", "erms", "invpcid", "rtm",
1084 NULL, "zero-fcs-fds", "mpx", NULL,
1085 "avx512f", "avx512dq", "rdseed", "adx",
1086 "smap", "avx512ifma", "pcommit", "clflushopt",
1087 "clwb", "intel-pt", "avx512pf", "avx512er",
1088 "avx512cd", "sha-ni", "avx512bw", "avx512vl",
1089 },
1090 .cpuid = {
1091 .eax = 7,
1092 .needs_ecx = true, .ecx = 0,
1093 .reg = R_EBX,
1094 },
1095 .tcg_features = TCG_7_0_EBX_FEATURES,
1096 },
1097 [FEAT_7_0_ECX] = {
1098 .type = CPUID_FEATURE_WORD,
1099 .feat_names = {
1100 NULL, "avx512vbmi", "umip", "pku",
1101 NULL /* ospke */, "waitpkg", "avx512vbmi2", NULL,
1102 "gfni", "vaes", "vpclmulqdq", "avx512vnni",
1103 "avx512bitalg", NULL, "avx512-vpopcntdq", NULL,
1104 "la57", NULL, NULL, NULL,
1105 NULL, NULL, "rdpid", NULL,
1106 "bus-lock-detect", "cldemote", NULL, "movdiri",
1107 "movdir64b", NULL, "sgxlc", "pks",
1108 },
1109 .cpuid = {
1110 .eax = 7,
1111 .needs_ecx = true, .ecx = 0,
1112 .reg = R_ECX,
1113 },
1114 .tcg_features = TCG_7_0_ECX_FEATURES,
1115 },
1116 [FEAT_7_0_EDX] = {
1117 .type = CPUID_FEATURE_WORD,
1118 .feat_names = {
1119 NULL, NULL, "avx512-4vnniw", "avx512-4fmaps",
1120 "fsrm", NULL, NULL, NULL,
1121 "avx512-vp2intersect", NULL, "md-clear", NULL,
1122 NULL, NULL, "serialize", NULL,
1123 "tsx-ldtrk", NULL, NULL /* pconfig */, "arch-lbr",
1124 NULL, NULL, "amx-bf16", "avx512-fp16",
1125 "amx-tile", "amx-int8", "spec-ctrl", "stibp",
1126 "flush-l1d", "arch-capabilities", "core-capability", "ssbd",
1127 },
1128 .cpuid = {
1129 .eax = 7,
1130 .needs_ecx = true, .ecx = 0,
1131 .reg = R_EDX,
1132 },
1133 .tcg_features = TCG_7_0_EDX_FEATURES,
1134 },
1135 [FEAT_7_1_EAX] = {
1136 .type = CPUID_FEATURE_WORD,
1137 .feat_names = {
1138 "sha512", "sm3", "sm4", NULL,
1139 "avx-vnni", "avx512-bf16", NULL, "cmpccxadd",
1140 NULL, NULL, "fzrm", "fsrs",
1141 "fsrc", NULL, NULL, NULL,
1142 NULL, "fred", "lkgs", "wrmsrns",
1143 NULL, "amx-fp16", NULL, "avx-ifma",
1144 NULL, NULL, "lam", NULL,
1145 NULL, NULL, NULL, NULL,
1146 },
1147 .cpuid = {
1148 .eax = 7,
1149 .needs_ecx = true, .ecx = 1,
1150 .reg = R_EAX,
1151 },
1152 .tcg_features = TCG_7_1_EAX_FEATURES,
1153 },
1154 [FEAT_7_1_ECX] = {
1155 .type = CPUID_FEATURE_WORD,
1156 .feat_names = {
1157 NULL, NULL, NULL, NULL,
1158 NULL, "msr-imm", NULL, NULL,
1159 NULL, NULL, NULL, NULL,
1160 NULL, NULL, NULL, NULL,
1161 NULL, NULL, NULL, NULL,
1162 NULL, NULL, NULL, NULL,
1163 NULL, NULL, NULL, NULL,
1164 NULL, NULL, NULL, NULL,
1165 },
1166 .cpuid = {
1167 .eax = 7,
1168 .needs_ecx = true, .ecx = 1,
1169 .reg = R_ECX,
1170 },
1171 .tcg_features = TCG_7_1_ECX_FEATURES,
1172 },
1173 [FEAT_7_1_EDX] = {
1174 .type = CPUID_FEATURE_WORD,
1175 .feat_names = {
1176 NULL, NULL, NULL, NULL,
1177 "avx-vnni-int8", "avx-ne-convert", NULL, NULL,
1178 "amx-complex", NULL, "avx-vnni-int16", NULL,
1179 NULL, NULL, "prefetchiti", NULL,
1180 NULL, NULL, NULL, "avx10",
1181 NULL, NULL, NULL, NULL,
1182 NULL, NULL, NULL, NULL,
1183 NULL, NULL, NULL, NULL,
1184 },
1185 .cpuid = {
1186 .eax = 7,
1187 .needs_ecx = true, .ecx = 1,
1188 .reg = R_EDX,
1189 },
1190 .tcg_features = TCG_7_1_EDX_FEATURES,
1191 },
1192 [FEAT_7_2_EDX] = {
1193 .type = CPUID_FEATURE_WORD,
1194 .feat_names = {
1195 "intel-psfd", "ipred-ctrl", "rrsba-ctrl", "ddpd-u",
1196 "bhi-ctrl", "mcdt-no", NULL, NULL,
1197 NULL, NULL, NULL, NULL,
1198 NULL, NULL, NULL, NULL,
1199 NULL, NULL, NULL, NULL,
1200 NULL, NULL, NULL, NULL,
1201 NULL, NULL, NULL, NULL,
1202 NULL, NULL, NULL, NULL,
1203 },
1204 .cpuid = {
1205 .eax = 7,
1206 .needs_ecx = true, .ecx = 2,
1207 .reg = R_EDX,
1208 },
1209 .tcg_features = TCG_7_2_EDX_FEATURES,
1210 },
1211 [FEAT_24_0_EBX] = {
1212 .type = CPUID_FEATURE_WORD,
1213 .feat_names = {
1214 [16] = "avx10-128",
1215 [17] = "avx10-256",
1216 [18] = "avx10-512",
1217 },
1218 .cpuid = {
1219 .eax = 0x24,
1220 .needs_ecx = true, .ecx = 0,
1221 .reg = R_EBX,
1222 },
1223 .tcg_features = TCG_24_0_EBX_FEATURES,
1224 },
1225 [FEAT_8000_0007_EDX] = {
1226 .type = CPUID_FEATURE_WORD,
1227 .feat_names = {
1228 NULL, NULL, NULL, NULL,
1229 NULL, NULL, NULL, NULL,
1230 "invtsc", NULL, NULL, NULL,
1231 NULL, NULL, NULL, NULL,
1232 NULL, NULL, NULL, NULL,
1233 NULL, NULL, NULL, NULL,
1234 NULL, NULL, NULL, NULL,
1235 NULL, NULL, NULL, NULL,
1236 },
1237 .cpuid = { .eax = 0x80000007, .reg = R_EDX, },
1238 .tcg_features = TCG_APM_FEATURES,
1239 .unmigratable_flags = CPUID_APM_INVTSC,
1240 },
1241 [FEAT_8000_0007_EBX] = {
1242 .type = CPUID_FEATURE_WORD,
1243 .feat_names = {
1244 "overflow-recov", "succor", NULL, NULL,
1245 NULL, NULL, NULL, NULL,
1246 NULL, NULL, NULL, NULL,
1247 NULL, NULL, NULL, NULL,
1248 NULL, NULL, NULL, NULL,
1249 NULL, NULL, NULL, NULL,
1250 NULL, NULL, NULL, NULL,
1251 NULL, NULL, NULL, NULL,
1252 },
1253 .cpuid = { .eax = 0x80000007, .reg = R_EBX, },
1254 .tcg_features = 0,
1255 .unmigratable_flags = 0,
1256 },
1257 [FEAT_8000_0008_EBX] = {
1258 .type = CPUID_FEATURE_WORD,
1259 .feat_names = {
1260 "clzero", NULL, "xsaveerptr", NULL,
1261 NULL, NULL, NULL, NULL,
1262 NULL, "wbnoinvd", NULL, NULL,
1263 "ibpb", NULL, "ibrs", "amd-stibp",
1264 NULL, "stibp-always-on", NULL, NULL,
1265 NULL, NULL, NULL, NULL,
1266 "amd-ssbd", "virt-ssbd", "amd-no-ssb", NULL,
1267 "amd-psfd", NULL, NULL, NULL,
1268 },
1269 .cpuid = { .eax = 0x80000008, .reg = R_EBX, },
1270 .tcg_features = TCG_8000_0008_EBX,
1271 .unmigratable_flags = 0,
1272 },
1273 [FEAT_8000_0021_EAX] = {
1274 .type = CPUID_FEATURE_WORD,
1275 .feat_names = {
1276 "no-nested-data-bp", "fs-gs-base-ns", "lfence-always-serializing", NULL,
1277 NULL, NULL, "null-sel-clr-base", NULL,
1278 "auto-ibrs", NULL, NULL, NULL,
1279 NULL, NULL, NULL, NULL,
1280 NULL, NULL, NULL, NULL,
1281 "prefetchi", NULL, NULL, NULL,
1282 "eraps", NULL, NULL, "sbpb",
1283 "ibpb-brtype", "srso-no", "srso-user-kernel-no", NULL,
1284 },
1285 .cpuid = { .eax = 0x80000021, .reg = R_EAX, },
1286 .tcg_features = TCG_8000_0021_EAX_FEATURES,
1287 .unmigratable_flags = 0,
1288 },
1289 [FEAT_8000_0021_EBX] = {
1290 .type = CPUID_FEATURE_WORD,
1291 .cpuid = { .eax = 0x80000021, .reg = R_EBX, },
1292 .tcg_features = 0,
1293 .unmigratable_flags = 0,
1294 },
1295 [FEAT_8000_0022_EAX] = {
1296 .type = CPUID_FEATURE_WORD,
1297 .feat_names = {
1298 "perfmon-v2", NULL, NULL, NULL,
1299 NULL, NULL, NULL, NULL,
1300 NULL, NULL, NULL, NULL,
1301 NULL, NULL, NULL, NULL,
1302 NULL, NULL, NULL, NULL,
1303 NULL, NULL, NULL, NULL,
1304 NULL, NULL, NULL, NULL,
1305 NULL, NULL, NULL, NULL,
1306 },
1307 .cpuid = { .eax = 0x80000022, .reg = R_EAX, },
1308 .tcg_features = 0,
1309 .unmigratable_flags = 0,
1310 },
1311 [FEAT_XSAVE] = {
1312 .type = CPUID_FEATURE_WORD,
1313 .feat_names = {
1314 "xsaveopt", "xsavec", "xgetbv1", "xsaves",
1315 "xfd", NULL, NULL, NULL,
1316 NULL, NULL, NULL, NULL,
1317 NULL, NULL, NULL, NULL,
1318 NULL, NULL, NULL, NULL,
1319 NULL, NULL, NULL, NULL,
1320 NULL, NULL, NULL, NULL,
1321 NULL, NULL, NULL, NULL,
1322 },
1323 .cpuid = {
1324 .eax = 0xd,
1325 .needs_ecx = true, .ecx = 1,
1326 .reg = R_EAX,
1327 },
1328 .tcg_features = TCG_XSAVE_FEATURES,
1329 },
1330 [FEAT_XSAVE_XSS_LO] = {
1331 .type = CPUID_FEATURE_WORD,
1332 .feat_names = {
1333 NULL, NULL, NULL, NULL,
1334 NULL, NULL, NULL, NULL,
1335 NULL, NULL, NULL, NULL,
1336 NULL, NULL, NULL, NULL,
1337 NULL, NULL, NULL, NULL,
1338 NULL, NULL, NULL, NULL,
1339 NULL, NULL, NULL, NULL,
1340 NULL, NULL, NULL, NULL,
1341 },
1342 .cpuid = {
1343 .eax = 0xD,
1344 .needs_ecx = true,
1345 .ecx = 1,
1346 .reg = R_ECX,
1347 },
1348 },
1349 [FEAT_XSAVE_XSS_HI] = {
1350 .type = CPUID_FEATURE_WORD,
1351 .cpuid = {
1352 .eax = 0xD,
1353 .needs_ecx = true,
1354 .ecx = 1,
1355 .reg = R_EDX
1356 },
1357 },
1358 [FEAT_6_EAX] = {
1359 .type = CPUID_FEATURE_WORD,
1360 .feat_names = {
1361 NULL, NULL, "arat", NULL,
1362 NULL, NULL, NULL, NULL,
1363 NULL, NULL, NULL, NULL,
1364 NULL, NULL, NULL, NULL,
1365 NULL, NULL, NULL, NULL,
1366 NULL, NULL, NULL, NULL,
1367 NULL, NULL, NULL, NULL,
1368 NULL, NULL, NULL, NULL,
1369 },
1370 .cpuid = { .eax = 6, .reg = R_EAX, },
1371 .tcg_features = TCG_6_EAX_FEATURES,
1372 },
1373 [FEAT_XSAVE_XCR0_LO] = {
1374 .type = CPUID_FEATURE_WORD,
1375 .cpuid = {
1376 .eax = 0xD,
1377 .needs_ecx = true, .ecx = 0,
1378 .reg = R_EAX,
1379 },
1380 .tcg_features = XSTATE_FP_MASK | XSTATE_SSE_MASK |
1381 XSTATE_YMM_MASK | XSTATE_BNDREGS_MASK | XSTATE_BNDCSR_MASK |
1382 XSTATE_PKRU_MASK,
1383 .migratable_flags = XSTATE_FP_MASK | XSTATE_SSE_MASK |
1384 XSTATE_YMM_MASK | XSTATE_BNDREGS_MASK | XSTATE_BNDCSR_MASK |
1385 XSTATE_OPMASK_MASK | XSTATE_ZMM_Hi256_MASK | XSTATE_Hi16_ZMM_MASK |
1386 XSTATE_PKRU_MASK,
1387 },
1388 [FEAT_XSAVE_XCR0_HI] = {
1389 .type = CPUID_FEATURE_WORD,
1390 .cpuid = {
1391 .eax = 0xD,
1392 .needs_ecx = true, .ecx = 0,
1393 .reg = R_EDX,
1394 },
1395 .tcg_features = 0U,
1396 },
1397 /*Below are MSR exposed features*/
1398 [FEAT_ARCH_CAPABILITIES] = {
1399 .type = MSR_FEATURE_WORD,
1400 .feat_names = {
1401 "rdctl-no", "ibrs-all", "rsba", "skip-l1dfl-vmentry",
1402 "ssb-no", "mds-no", "pschange-mc-no", "tsx-ctrl",
1403 "taa-no", NULL, NULL, NULL,
1404 NULL, "sbdr-ssdp-no", "fbsdp-no", "psdp-no",
1405 NULL, "fb-clear", NULL, NULL,
1406 "bhi-no", NULL, NULL, NULL,
1407 "pbrsb-no", NULL, "gds-no", "rfds-no",
1408 "rfds-clear", NULL, NULL, NULL,
1409 NULL, NULL, NULL, NULL,
1410 NULL, NULL, NULL, NULL,
1411 NULL, NULL, NULL, NULL,
1412 NULL, NULL, NULL, NULL,
1413 NULL, NULL, NULL, NULL,
1414 NULL, NULL, NULL, NULL,
1415 NULL, NULL, NULL, NULL,
1416 NULL, NULL, "its-no", NULL,
1417 },
1418 .msr = {
1419 .index = MSR_IA32_ARCH_CAPABILITIES,
1420 },
1421 /*
1422 * FEAT_ARCH_CAPABILITIES only affects a read-only MSR, which
1423 * cannot be read from user mode. Therefore, it has no impact
1424 > on any user-mode operation, and warnings about unsupported
1425 * features do not matter.
1426 */
1427 .tcg_features = ~0U,
1428 },
1429 [FEAT_CORE_CAPABILITY] = {
1430 .type = MSR_FEATURE_WORD,
1431 .feat_names = {
1432 NULL, NULL, NULL, NULL,
1433 NULL, "split-lock-detect", NULL, NULL,
1434 NULL, NULL, NULL, NULL,
1435 NULL, NULL, NULL, NULL,
1436 NULL, NULL, NULL, NULL,
1437 NULL, NULL, NULL, NULL,
1438 NULL, NULL, NULL, NULL,
1439 NULL, NULL, NULL, NULL,
1440 },
1441 .msr = {
1442 .index = MSR_IA32_CORE_CAPABILITY,
1443 },
1444 },
1445 [FEAT_PERF_CAPABILITIES] = {
1446 .type = MSR_FEATURE_WORD,
1447 .feat_names = {
1448 NULL, NULL, NULL, NULL,
1449 NULL, NULL, NULL, NULL,
1450 NULL, NULL, NULL, NULL,
1451 NULL, "full-width-write", NULL, NULL,
1452 NULL, NULL, NULL, NULL,
1453 NULL, NULL, NULL, NULL,
1454 NULL, NULL, NULL, NULL,
1455 NULL, NULL, NULL, NULL,
1456 },
1457 .msr = {
1458 .index = MSR_IA32_PERF_CAPABILITIES,
1459 },
1460 },
1461
1462 [FEAT_VMX_PROCBASED_CTLS] = {
1463 .type = MSR_FEATURE_WORD,
1464 .feat_names = {
1465 NULL, NULL, "vmx-vintr-pending", "vmx-tsc-offset",
1466 NULL, NULL, NULL, "vmx-hlt-exit",
1467 NULL, "vmx-invlpg-exit", "vmx-mwait-exit", "vmx-rdpmc-exit",
1468 "vmx-rdtsc-exit", NULL, NULL, "vmx-cr3-load-noexit",
1469 "vmx-cr3-store-noexit", NULL, NULL, "vmx-cr8-load-exit",
1470 "vmx-cr8-store-exit", "vmx-flexpriority", "vmx-vnmi-pending", "vmx-movdr-exit",
1471 "vmx-io-exit", "vmx-io-bitmap", NULL, "vmx-mtf",
1472 "vmx-msr-bitmap", "vmx-monitor-exit", "vmx-pause-exit", "vmx-secondary-ctls",
1473 },
1474 .msr = {
1475 .index = MSR_IA32_VMX_TRUE_PROCBASED_CTLS,
1476 }
1477 },
1478
1479 [FEAT_VMX_SECONDARY_CTLS] = {
1480 .type = MSR_FEATURE_WORD,
1481 .feat_names = {
1482 "vmx-apicv-xapic", "vmx-ept", "vmx-desc-exit", "vmx-rdtscp-exit",
1483 "vmx-apicv-x2apic", "vmx-vpid", "vmx-wbinvd-exit", "vmx-unrestricted-guest",
1484 "vmx-apicv-register", "vmx-apicv-vid", "vmx-ple", "vmx-rdrand-exit",
1485 "vmx-invpcid-exit", "vmx-vmfunc", "vmx-shadow-vmcs", "vmx-encls-exit",
1486 "vmx-rdseed-exit", "vmx-pml", NULL, NULL,
1487 "vmx-xsaves", NULL, NULL, NULL,
1488 NULL, "vmx-tsc-scaling", "vmx-enable-user-wait-pause", NULL,
1489 NULL, NULL, NULL, NULL,
1490 },
1491 .msr = {
1492 .index = MSR_IA32_VMX_PROCBASED_CTLS2,
1493 }
1494 },
1495
1496 [FEAT_VMX_PINBASED_CTLS] = {
1497 .type = MSR_FEATURE_WORD,
1498 .feat_names = {
1499 "vmx-intr-exit", NULL, NULL, "vmx-nmi-exit",
1500 NULL, "vmx-vnmi", "vmx-preemption-timer", "vmx-posted-intr",
1501 NULL, NULL, NULL, NULL,
1502 NULL, NULL, NULL, NULL,
1503 NULL, NULL, NULL, NULL,
1504 NULL, NULL, NULL, NULL,
1505 NULL, NULL, NULL, NULL,
1506 NULL, NULL, NULL, NULL,
1507 },
1508 .msr = {
1509 .index = MSR_IA32_VMX_TRUE_PINBASED_CTLS,
1510 }
1511 },
1512
1513 [FEAT_VMX_EXIT_CTLS] = {
1514 .type = MSR_FEATURE_WORD,
1515 /*
1516 * VMX_VM_EXIT_HOST_ADDR_SPACE_SIZE is copied from
1517 * the LM CPUID bit.
1518 */
1519 .feat_names = {
1520 NULL, NULL, "vmx-exit-nosave-debugctl", NULL,
1521 NULL, NULL, NULL, NULL,
1522 NULL, NULL /* vmx-exit-host-addr-space-size */, NULL, NULL,
1523 "vmx-exit-load-perf-global-ctrl", NULL, NULL, "vmx-exit-ack-intr",
1524 NULL, NULL, "vmx-exit-save-pat", "vmx-exit-load-pat",
1525 "vmx-exit-save-efer", "vmx-exit-load-efer",
1526 "vmx-exit-save-preemption-timer", "vmx-exit-clear-bndcfgs",
1527 NULL, "vmx-exit-clear-rtit-ctl", NULL, NULL,
1528 NULL, "vmx-exit-load-pkrs", NULL, "vmx-exit-secondary-ctls",
1529 },
1530 .msr = {
1531 .index = MSR_IA32_VMX_TRUE_EXIT_CTLS,
1532 }
1533 },
1534
1535 [FEAT_VMX_ENTRY_CTLS] = {
1536 .type = MSR_FEATURE_WORD,
1537 .feat_names = {
1538 NULL, NULL, "vmx-entry-noload-debugctl", NULL,
1539 NULL, NULL, NULL, NULL,
1540 NULL, "vmx-entry-ia32e-mode", NULL, NULL,
1541 NULL, "vmx-entry-load-perf-global-ctrl", "vmx-entry-load-pat", "vmx-entry-load-efer",
1542 "vmx-entry-load-bndcfgs", NULL, "vmx-entry-load-rtit-ctl", NULL,
1543 NULL, NULL, "vmx-entry-load-pkrs", "vmx-entry-load-fred",
1544 NULL, NULL, NULL, NULL,
1545 NULL, NULL, NULL, NULL,
1546 },
1547 .msr = {
1548 .index = MSR_IA32_VMX_TRUE_ENTRY_CTLS,
1549 }
1550 },
1551
1552 [FEAT_VMX_MISC] = {
1553 .type = MSR_FEATURE_WORD,
1554 .feat_names = {
1555 NULL, NULL, NULL, NULL,
1556 NULL, "vmx-store-lma", "vmx-activity-hlt", "vmx-activity-shutdown",
1557 "vmx-activity-wait-sipi", NULL, NULL, NULL,
1558 NULL, NULL, NULL, NULL,
1559 NULL, NULL, NULL, NULL,
1560 NULL, NULL, NULL, NULL,
1561 NULL, NULL, NULL, NULL,
1562 NULL, "vmx-vmwrite-vmexit-fields", "vmx-zero-len-inject", NULL,
1563 },
1564 .msr = {
1565 .index = MSR_IA32_VMX_MISC,
1566 }
1567 },
1568
1569 [FEAT_VMX_EPT_VPID_CAPS] = {
1570 .type = MSR_FEATURE_WORD,
1571 .feat_names = {
1572 "vmx-ept-execonly", NULL, NULL, NULL,
1573 NULL, NULL, "vmx-page-walk-4", "vmx-page-walk-5",
1574 NULL, NULL, NULL, NULL,
1575 NULL, NULL, NULL, NULL,
1576 "vmx-ept-2mb", "vmx-ept-1gb", NULL, NULL,
1577 "vmx-invept", "vmx-eptad", "vmx-ept-advanced-exitinfo", NULL,
1578 NULL, "vmx-invept-single-context", "vmx-invept-all-context", NULL,
1579 NULL, NULL, NULL, NULL,
1580 "vmx-invvpid", NULL, NULL, NULL,
1581 NULL, NULL, NULL, NULL,
1582 "vmx-invvpid-single-addr", "vmx-invept-single-context",
1583 "vmx-invvpid-all-context", "vmx-invept-single-context-noglobals",
1584 NULL, NULL, NULL, NULL,
1585 NULL, NULL, NULL, NULL,
1586 NULL, NULL, NULL, NULL,
1587 NULL, NULL, NULL, NULL,
1588 NULL, NULL, NULL, NULL,
1589 },
1590 .msr = {
1591 .index = MSR_IA32_VMX_EPT_VPID_CAP,
1592 }
1593 },
1594
1595 [FEAT_VMX_BASIC] = {
1596 .type = MSR_FEATURE_WORD,
1597 .feat_names = {
1598 [54] = "vmx-ins-outs",
1599 [55] = "vmx-true-ctls",
1600 [56] = "vmx-any-errcode",
1601 [58] = "vmx-nested-exception",
1602 },
1603 .msr = {
1604 .index = MSR_IA32_VMX_BASIC,
1605 },
1606 /* Just to be safe - we don't support setting the MSEG version field. */
1607 .no_autoenable_flags = MSR_VMX_BASIC_DUAL_MONITOR,
1608 },
1609
1610 [FEAT_VMX_VMFUNC] = {
1611 .type = MSR_FEATURE_WORD,
1612 .feat_names = {
1613 [0] = "vmx-eptp-switching",
1614 },
1615 .msr = {
1616 .index = MSR_IA32_VMX_VMFUNC,
1617 }
1618 },
1619
1620 [FEAT_14_0_ECX] = {
1621 .type = CPUID_FEATURE_WORD,
1622 .feat_names = {
1623 NULL, NULL, NULL, NULL,
1624 NULL, NULL, NULL, NULL,
1625 NULL, NULL, NULL, NULL,
1626 NULL, NULL, NULL, NULL,
1627 NULL, NULL, NULL, NULL,
1628 NULL, NULL, NULL, NULL,
1629 NULL, NULL, NULL, NULL,
1630 NULL, NULL, NULL, "intel-pt-lip",
1631 },
1632 .cpuid = {
1633 .eax = 0x14,
1634 .needs_ecx = true, .ecx = 0,
1635 .reg = R_ECX,
1636 },
1637 .tcg_features = TCG_14_0_ECX_FEATURES,
1638 },
1639
1640 [FEAT_SGX_12_0_EAX] = {
1641 .type = CPUID_FEATURE_WORD,
1642 .feat_names = {
1643 "sgx1", "sgx2", NULL, NULL,
1644 NULL, NULL, NULL, NULL,
1645 NULL, NULL, NULL, "sgx-edeccssa",
1646 NULL, NULL, NULL, NULL,
1647 NULL, NULL, NULL, NULL,
1648 NULL, NULL, NULL, NULL,
1649 NULL, NULL, NULL, NULL,
1650 NULL, NULL, NULL, NULL,
1651 },
1652 .cpuid = {
1653 .eax = 0x12,
1654 .needs_ecx = true, .ecx = 0,
1655 .reg = R_EAX,
1656 },
1657 .tcg_features = TCG_SGX_12_0_EAX_FEATURES,
1658 },
1659
1660 [FEAT_SGX_12_0_EBX] = {
1661 .type = CPUID_FEATURE_WORD,
1662 .feat_names = {
1663 "sgx-exinfo" , NULL, NULL, NULL,
1664 NULL, NULL, NULL, NULL,
1665 NULL, NULL, NULL, NULL,
1666 NULL, NULL, NULL, NULL,
1667 NULL, NULL, NULL, NULL,
1668 NULL, NULL, NULL, NULL,
1669 NULL, NULL, NULL, NULL,
1670 NULL, NULL, NULL, NULL,
1671 },
1672 .cpuid = {
1673 .eax = 0x12,
1674 .needs_ecx = true, .ecx = 0,
1675 .reg = R_EBX,
1676 },
1677 .tcg_features = TCG_SGX_12_0_EBX_FEATURES,
1678 },
1679
1680 [FEAT_SGX_12_1_EAX] = {
1681 .type = CPUID_FEATURE_WORD,
1682 .feat_names = {
1683 NULL, "sgx-debug", "sgx-mode64", NULL,
1684 "sgx-provisionkey", "sgx-tokenkey", NULL, "sgx-kss",
1685 NULL, NULL, "sgx-aex-notify", NULL,
1686 NULL, NULL, NULL, NULL,
1687 NULL, NULL, NULL, NULL,
1688 NULL, NULL, NULL, NULL,
1689 NULL, NULL, NULL, NULL,
1690 NULL, NULL, NULL, NULL,
1691 },
1692 .cpuid = {
1693 .eax = 0x12,
1694 .needs_ecx = true, .ecx = 1,
1695 .reg = R_EAX,
1696 },
1697 .tcg_features = TCG_SGX_12_1_EAX_FEATURES,
1698 },
1699 };
1700
is_feature_word_cpuid(uint32_t feature,uint32_t index,int reg)1701 bool is_feature_word_cpuid(uint32_t feature, uint32_t index, int reg)
1702 {
1703 FeatureWordInfo *wi;
1704 FeatureWord w;
1705
1706 for (w = 0; w < FEATURE_WORDS; w++) {
1707 wi = &feature_word_info[w];
1708 if (wi->type == CPUID_FEATURE_WORD && wi->cpuid.eax == feature &&
1709 (!wi->cpuid.needs_ecx || wi->cpuid.ecx == index) &&
1710 wi->cpuid.reg == reg) {
1711 return true;
1712 }
1713 }
1714 return false;
1715 }
1716
1717 static FeatureDep feature_dependencies[] = {
1718 {
1719 .from = { FEAT_7_0_EDX, CPUID_7_0_EDX_ARCH_CAPABILITIES },
1720 .to = { FEAT_ARCH_CAPABILITIES, ~0ull },
1721 },
1722 {
1723 .from = { FEAT_7_0_EDX, CPUID_7_0_EDX_CORE_CAPABILITY },
1724 .to = { FEAT_CORE_CAPABILITY, ~0ull },
1725 },
1726 {
1727 .from = { FEAT_1_ECX, CPUID_EXT_PDCM },
1728 .to = { FEAT_PERF_CAPABILITIES, ~0ull },
1729 },
1730 {
1731 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1732 .to = { FEAT_VMX_PROCBASED_CTLS, ~0ull },
1733 },
1734 {
1735 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1736 .to = { FEAT_VMX_PINBASED_CTLS, ~0ull },
1737 },
1738 {
1739 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1740 .to = { FEAT_VMX_EXIT_CTLS, ~0ull },
1741 },
1742 {
1743 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1744 .to = { FEAT_VMX_ENTRY_CTLS, ~0ull },
1745 },
1746 {
1747 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1748 .to = { FEAT_VMX_MISC, ~0ull },
1749 },
1750 {
1751 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1752 .to = { FEAT_VMX_BASIC, ~0ull },
1753 },
1754 {
1755 .from = { FEAT_8000_0001_EDX, CPUID_EXT2_LM },
1756 .to = { FEAT_VMX_ENTRY_CTLS, VMX_VM_ENTRY_IA32E_MODE },
1757 },
1758 {
1759 .from = { FEAT_VMX_PROCBASED_CTLS, VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS },
1760 .to = { FEAT_VMX_SECONDARY_CTLS, ~0ull },
1761 },
1762 {
1763 .from = { FEAT_XSAVE, CPUID_XSAVE_XSAVES },
1764 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_XSAVES },
1765 },
1766 {
1767 .from = { FEAT_1_ECX, CPUID_EXT_RDRAND },
1768 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_RDRAND_EXITING },
1769 },
1770 {
1771 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_INVPCID },
1772 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_INVPCID },
1773 },
1774 {
1775 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_MPX },
1776 .to = { FEAT_VMX_EXIT_CTLS, VMX_VM_EXIT_CLEAR_BNDCFGS },
1777 },
1778 {
1779 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_MPX },
1780 .to = { FEAT_VMX_ENTRY_CTLS, VMX_VM_ENTRY_LOAD_BNDCFGS },
1781 },
1782 {
1783 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_RDSEED },
1784 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_RDSEED_EXITING },
1785 },
1786 {
1787 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_INTEL_PT },
1788 .to = { FEAT_14_0_ECX, ~0ull },
1789 },
1790 {
1791 .from = { FEAT_8000_0001_EDX, CPUID_EXT2_RDTSCP },
1792 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_RDTSCP },
1793 },
1794 {
1795 .from = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_EPT },
1796 .to = { FEAT_VMX_EPT_VPID_CAPS, 0xffffffffull },
1797 },
1798 {
1799 .from = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_EPT },
1800 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST },
1801 },
1802 {
1803 .from = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_VPID },
1804 .to = { FEAT_VMX_EPT_VPID_CAPS, 0xffffffffull << 32 },
1805 },
1806 {
1807 .from = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_VMFUNC },
1808 .to = { FEAT_VMX_VMFUNC, ~0ull },
1809 },
1810 {
1811 .from = { FEAT_8000_0001_ECX, CPUID_EXT3_SVM },
1812 .to = { FEAT_SVM, ~0ull },
1813 },
1814 {
1815 .from = { FEAT_7_0_ECX, CPUID_7_0_ECX_WAITPKG },
1816 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_USER_WAIT_PAUSE },
1817 },
1818 {
1819 .from = { FEAT_8000_0001_EDX, CPUID_EXT2_LM },
1820 .to = { FEAT_7_1_EAX, CPUID_7_1_EAX_FRED },
1821 },
1822 {
1823 .from = { FEAT_7_1_EAX, CPUID_7_1_EAX_LKGS },
1824 .to = { FEAT_7_1_EAX, CPUID_7_1_EAX_FRED },
1825 },
1826 {
1827 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_SGX },
1828 .to = { FEAT_7_0_ECX, CPUID_7_0_ECX_SGX_LC },
1829 },
1830 {
1831 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_SGX },
1832 .to = { FEAT_SGX_12_0_EAX, ~0ull },
1833 },
1834 {
1835 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_SGX },
1836 .to = { FEAT_SGX_12_0_EBX, ~0ull },
1837 },
1838 {
1839 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_SGX },
1840 .to = { FEAT_SGX_12_1_EAX, ~0ull },
1841 },
1842 {
1843 .from = { FEAT_24_0_EBX, CPUID_24_0_EBX_AVX10_128 },
1844 .to = { FEAT_24_0_EBX, CPUID_24_0_EBX_AVX10_256 },
1845 },
1846 {
1847 .from = { FEAT_24_0_EBX, CPUID_24_0_EBX_AVX10_256 },
1848 .to = { FEAT_24_0_EBX, CPUID_24_0_EBX_AVX10_512 },
1849 },
1850 {
1851 .from = { FEAT_24_0_EBX, CPUID_24_0_EBX_AVX10_VL_MASK },
1852 .to = { FEAT_7_1_EDX, CPUID_7_1_EDX_AVX10 },
1853 },
1854 {
1855 .from = { FEAT_7_1_EDX, CPUID_7_1_EDX_AVX10 },
1856 .to = { FEAT_24_0_EBX, ~0ull },
1857 },
1858 };
1859
1860 typedef struct X86RegisterInfo32 {
1861 /* Name of register */
1862 const char *name;
1863 /* QAPI enum value register */
1864 X86CPURegister32 qapi_enum;
1865 } X86RegisterInfo32;
1866
1867 #define REGISTER(reg) \
1868 [R_##reg] = { .name = #reg, .qapi_enum = X86_CPU_REGISTER32_##reg }
1869 static const X86RegisterInfo32 x86_reg_info_32[CPU_NB_REGS32] = {
1870 REGISTER(EAX),
1871 REGISTER(ECX),
1872 REGISTER(EDX),
1873 REGISTER(EBX),
1874 REGISTER(ESP),
1875 REGISTER(EBP),
1876 REGISTER(ESI),
1877 REGISTER(EDI),
1878 };
1879 #undef REGISTER
1880
1881 ExtSaveArea x86_ext_save_areas[XSAVE_STATE_AREA_COUNT] = {
1882 [XSTATE_FP_BIT] = {
1883 /* x87 FP state component is always enabled if XSAVE is supported */
1884 .feature = FEAT_1_ECX, .bits = CPUID_EXT_XSAVE,
1885 .size = sizeof(X86LegacyXSaveArea) + sizeof(X86XSaveHeader),
1886 },
1887 [XSTATE_SSE_BIT] = {
1888 /* SSE state component is always enabled if XSAVE is supported */
1889 .feature = FEAT_1_ECX, .bits = CPUID_EXT_XSAVE,
1890 .size = sizeof(X86LegacyXSaveArea) + sizeof(X86XSaveHeader),
1891 },
1892 [XSTATE_YMM_BIT] =
1893 { .feature = FEAT_1_ECX, .bits = CPUID_EXT_AVX,
1894 .size = sizeof(XSaveAVX) },
1895 [XSTATE_BNDREGS_BIT] =
1896 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_MPX,
1897 .size = sizeof(XSaveBNDREG) },
1898 [XSTATE_BNDCSR_BIT] =
1899 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_MPX,
1900 .size = sizeof(XSaveBNDCSR) },
1901 [XSTATE_OPMASK_BIT] =
1902 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_AVX512F,
1903 .size = sizeof(XSaveOpmask) },
1904 [XSTATE_ZMM_Hi256_BIT] =
1905 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_AVX512F,
1906 .size = sizeof(XSaveZMM_Hi256) },
1907 [XSTATE_Hi16_ZMM_BIT] =
1908 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_AVX512F,
1909 .size = sizeof(XSaveHi16_ZMM) },
1910 [XSTATE_PKRU_BIT] =
1911 { .feature = FEAT_7_0_ECX, .bits = CPUID_7_0_ECX_PKU,
1912 .size = sizeof(XSavePKRU) },
1913 [XSTATE_ARCH_LBR_BIT] = {
1914 .feature = FEAT_7_0_EDX, .bits = CPUID_7_0_EDX_ARCH_LBR,
1915 .offset = 0 /*supervisor mode component, offset = 0 */,
1916 .size = sizeof(XSavesArchLBR) },
1917 [XSTATE_XTILE_CFG_BIT] = {
1918 .feature = FEAT_7_0_EDX, .bits = CPUID_7_0_EDX_AMX_TILE,
1919 .size = sizeof(XSaveXTILECFG),
1920 },
1921 [XSTATE_XTILE_DATA_BIT] = {
1922 .feature = FEAT_7_0_EDX, .bits = CPUID_7_0_EDX_AMX_TILE,
1923 .size = sizeof(XSaveXTILEDATA)
1924 },
1925 };
1926
xsave_area_size(uint64_t mask,bool compacted)1927 uint32_t xsave_area_size(uint64_t mask, bool compacted)
1928 {
1929 uint64_t ret = x86_ext_save_areas[0].size;
1930 const ExtSaveArea *esa;
1931 uint32_t offset = 0;
1932 int i;
1933
1934 for (i = 2; i < ARRAY_SIZE(x86_ext_save_areas); i++) {
1935 esa = &x86_ext_save_areas[i];
1936 if ((mask >> i) & 1) {
1937 offset = compacted ? ret : esa->offset;
1938 ret = MAX(ret, offset + esa->size);
1939 }
1940 }
1941 return ret;
1942 }
1943
accel_uses_host_cpuid(void)1944 static inline bool accel_uses_host_cpuid(void)
1945 {
1946 return kvm_enabled() || hvf_enabled();
1947 }
1948
x86_cpu_xsave_xcr0_components(X86CPU * cpu)1949 static inline uint64_t x86_cpu_xsave_xcr0_components(X86CPU *cpu)
1950 {
1951 return ((uint64_t)cpu->env.features[FEAT_XSAVE_XCR0_HI]) << 32 |
1952 cpu->env.features[FEAT_XSAVE_XCR0_LO];
1953 }
1954
1955 /* Return name of 32-bit register, from a R_* constant */
get_register_name_32(unsigned int reg)1956 static const char *get_register_name_32(unsigned int reg)
1957 {
1958 if (reg >= CPU_NB_REGS32) {
1959 return NULL;
1960 }
1961 return x86_reg_info_32[reg].name;
1962 }
1963
x86_cpu_xsave_xss_components(X86CPU * cpu)1964 static inline uint64_t x86_cpu_xsave_xss_components(X86CPU *cpu)
1965 {
1966 return ((uint64_t)cpu->env.features[FEAT_XSAVE_XSS_HI]) << 32 |
1967 cpu->env.features[FEAT_XSAVE_XSS_LO];
1968 }
1969
1970 /*
1971 * Returns the set of feature flags that are supported and migratable by
1972 * QEMU, for a given FeatureWord.
1973 */
x86_cpu_get_migratable_flags(X86CPU * cpu,FeatureWord w)1974 static uint64_t x86_cpu_get_migratable_flags(X86CPU *cpu, FeatureWord w)
1975 {
1976 FeatureWordInfo *wi = &feature_word_info[w];
1977 CPUX86State *env = &cpu->env;
1978 uint64_t r = 0;
1979 int i;
1980
1981 for (i = 0; i < 64; i++) {
1982 uint64_t f = 1ULL << i;
1983
1984 /* If the feature name is known, it is implicitly considered migratable,
1985 * unless it is explicitly set in unmigratable_flags */
1986 if ((wi->migratable_flags & f) ||
1987 (wi->feat_names[i] && !(wi->unmigratable_flags & f))) {
1988 r |= f;
1989 }
1990 }
1991
1992 /* when tsc-khz is set explicitly, invtsc is migratable */
1993 if ((w == FEAT_8000_0007_EDX) && env->user_tsc_khz) {
1994 r |= CPUID_APM_INVTSC;
1995 }
1996
1997 return r;
1998 }
1999
host_cpuid(uint32_t function,uint32_t count,uint32_t * eax,uint32_t * ebx,uint32_t * ecx,uint32_t * edx)2000 void host_cpuid(uint32_t function, uint32_t count,
2001 uint32_t *eax, uint32_t *ebx, uint32_t *ecx, uint32_t *edx)
2002 {
2003 uint32_t vec[4];
2004
2005 #ifdef __x86_64__
2006 asm volatile("cpuid"
2007 : "=a"(vec[0]), "=b"(vec[1]),
2008 "=c"(vec[2]), "=d"(vec[3])
2009 : "0"(function), "c"(count) : "cc");
2010 #elif defined(__i386__)
2011 asm volatile("pusha \n\t"
2012 "cpuid \n\t"
2013 "mov %%eax, 0(%2) \n\t"
2014 "mov %%ebx, 4(%2) \n\t"
2015 "mov %%ecx, 8(%2) \n\t"
2016 "mov %%edx, 12(%2) \n\t"
2017 "popa"
2018 : : "a"(function), "c"(count), "S"(vec)
2019 : "memory", "cc");
2020 #else
2021 abort();
2022 #endif
2023
2024 if (eax)
2025 *eax = vec[0];
2026 if (ebx)
2027 *ebx = vec[1];
2028 if (ecx)
2029 *ecx = vec[2];
2030 if (edx)
2031 *edx = vec[3];
2032 }
2033
2034 /* CPU class name definitions: */
2035
2036 /* Return type name for a given CPU model name
2037 * Caller is responsible for freeing the returned string.
2038 */
x86_cpu_type_name(const char * model_name)2039 static char *x86_cpu_type_name(const char *model_name)
2040 {
2041 return g_strdup_printf(X86_CPU_TYPE_NAME("%s"), model_name);
2042 }
2043
x86_cpu_class_by_name(const char * cpu_model)2044 static ObjectClass *x86_cpu_class_by_name(const char *cpu_model)
2045 {
2046 g_autofree char *typename = x86_cpu_type_name(cpu_model);
2047 return object_class_by_name(typename);
2048 }
2049
x86_cpu_class_get_model_name(X86CPUClass * cc)2050 static char *x86_cpu_class_get_model_name(X86CPUClass *cc)
2051 {
2052 const char *class_name = object_class_get_name(OBJECT_CLASS(cc));
2053 assert(g_str_has_suffix(class_name, X86_CPU_TYPE_SUFFIX));
2054 return cpu_model_from_type(class_name);
2055 }
2056
2057 typedef struct X86CPUVersionDefinition {
2058 X86CPUVersion version;
2059 const char *alias;
2060 const char *note;
2061 PropValue *props;
2062 const CPUCaches *const cache_info;
2063 } X86CPUVersionDefinition;
2064
2065 /* Base definition for a CPU model */
2066 typedef struct X86CPUDefinition {
2067 const char *name;
2068 uint32_t level;
2069 uint32_t xlevel;
2070 /* vendor is zero-terminated, 12 character ASCII string */
2071 char vendor[CPUID_VENDOR_SZ + 1];
2072 int family;
2073 int model;
2074 int stepping;
2075 uint8_t avx10_version;
2076 FeatureWordArray features;
2077 const char *model_id;
2078 const CPUCaches *const cache_info;
2079 /*
2080 * Definitions for alternative versions of CPU model.
2081 * List is terminated by item with version == 0.
2082 * If NULL, version 1 will be registered automatically.
2083 */
2084 const X86CPUVersionDefinition *versions;
2085 const char *deprecation_note;
2086 } X86CPUDefinition;
2087
2088 /* Reference to a specific CPU model version */
2089 struct X86CPUModel {
2090 /* Base CPU definition */
2091 const X86CPUDefinition *cpudef;
2092 /* CPU model version */
2093 X86CPUVersion version;
2094 const char *note;
2095 /*
2096 * If true, this is an alias CPU model.
2097 * This matters only for "-cpu help" and query-cpu-definitions
2098 */
2099 bool is_alias;
2100 };
2101
2102 /* Get full model name for CPU version */
x86_cpu_versioned_model_name(const X86CPUDefinition * cpudef,X86CPUVersion version)2103 static char *x86_cpu_versioned_model_name(const X86CPUDefinition *cpudef,
2104 X86CPUVersion version)
2105 {
2106 assert(version > 0);
2107 return g_strdup_printf("%s-v%d", cpudef->name, (int)version);
2108 }
2109
2110 static const X86CPUVersionDefinition *
x86_cpu_def_get_versions(const X86CPUDefinition * def)2111 x86_cpu_def_get_versions(const X86CPUDefinition *def)
2112 {
2113 /* When X86CPUDefinition::versions is NULL, we register only v1 */
2114 static const X86CPUVersionDefinition default_version_list[] = {
2115 { 1 },
2116 { /* end of list */ }
2117 };
2118
2119 return def->versions ?: default_version_list;
2120 }
2121
2122 static const CPUCaches epyc_cache_info = {
2123 .l1d_cache = &(CPUCacheInfo) {
2124 .type = DATA_CACHE,
2125 .level = 1,
2126 .size = 32 * KiB,
2127 .line_size = 64,
2128 .associativity = 8,
2129 .partitions = 1,
2130 .sets = 64,
2131 .lines_per_tag = 1,
2132 .self_init = 1,
2133 .no_invd_sharing = true,
2134 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2135 },
2136 .l1i_cache = &(CPUCacheInfo) {
2137 .type = INSTRUCTION_CACHE,
2138 .level = 1,
2139 .size = 64 * KiB,
2140 .line_size = 64,
2141 .associativity = 4,
2142 .partitions = 1,
2143 .sets = 256,
2144 .lines_per_tag = 1,
2145 .self_init = 1,
2146 .no_invd_sharing = true,
2147 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2148 },
2149 .l2_cache = &(CPUCacheInfo) {
2150 .type = UNIFIED_CACHE,
2151 .level = 2,
2152 .size = 512 * KiB,
2153 .line_size = 64,
2154 .associativity = 8,
2155 .partitions = 1,
2156 .sets = 1024,
2157 .lines_per_tag = 1,
2158 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2159 },
2160 .l3_cache = &(CPUCacheInfo) {
2161 .type = UNIFIED_CACHE,
2162 .level = 3,
2163 .size = 8 * MiB,
2164 .line_size = 64,
2165 .associativity = 16,
2166 .partitions = 1,
2167 .sets = 8192,
2168 .lines_per_tag = 1,
2169 .self_init = true,
2170 .inclusive = true,
2171 .complex_indexing = true,
2172 .share_level = CPU_TOPOLOGY_LEVEL_DIE,
2173 },
2174 };
2175
2176 static CPUCaches epyc_v4_cache_info = {
2177 .l1d_cache = &(CPUCacheInfo) {
2178 .type = DATA_CACHE,
2179 .level = 1,
2180 .size = 32 * KiB,
2181 .line_size = 64,
2182 .associativity = 8,
2183 .partitions = 1,
2184 .sets = 64,
2185 .lines_per_tag = 1,
2186 .self_init = 1,
2187 .no_invd_sharing = true,
2188 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2189 },
2190 .l1i_cache = &(CPUCacheInfo) {
2191 .type = INSTRUCTION_CACHE,
2192 .level = 1,
2193 .size = 64 * KiB,
2194 .line_size = 64,
2195 .associativity = 4,
2196 .partitions = 1,
2197 .sets = 256,
2198 .lines_per_tag = 1,
2199 .self_init = 1,
2200 .no_invd_sharing = true,
2201 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2202 },
2203 .l2_cache = &(CPUCacheInfo) {
2204 .type = UNIFIED_CACHE,
2205 .level = 2,
2206 .size = 512 * KiB,
2207 .line_size = 64,
2208 .associativity = 8,
2209 .partitions = 1,
2210 .sets = 1024,
2211 .lines_per_tag = 1,
2212 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2213 },
2214 .l3_cache = &(CPUCacheInfo) {
2215 .type = UNIFIED_CACHE,
2216 .level = 3,
2217 .size = 8 * MiB,
2218 .line_size = 64,
2219 .associativity = 16,
2220 .partitions = 1,
2221 .sets = 8192,
2222 .lines_per_tag = 1,
2223 .self_init = true,
2224 .inclusive = true,
2225 .complex_indexing = false,
2226 .share_level = CPU_TOPOLOGY_LEVEL_DIE,
2227 },
2228 };
2229
2230 static CPUCaches epyc_v5_cache_info = {
2231 .l1d_cache = &(CPUCacheInfo) {
2232 .type = DATA_CACHE,
2233 .level = 1,
2234 .size = 32 * KiB,
2235 .line_size = 64,
2236 .associativity = 8,
2237 .partitions = 1,
2238 .sets = 64,
2239 .lines_per_tag = 1,
2240 .self_init = true,
2241 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2242 },
2243 .l1i_cache = &(CPUCacheInfo) {
2244 .type = INSTRUCTION_CACHE,
2245 .level = 1,
2246 .size = 64 * KiB,
2247 .line_size = 64,
2248 .associativity = 4,
2249 .partitions = 1,
2250 .sets = 256,
2251 .lines_per_tag = 1,
2252 .self_init = true,
2253 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2254 },
2255 .l2_cache = &(CPUCacheInfo) {
2256 .type = UNIFIED_CACHE,
2257 .level = 2,
2258 .size = 512 * KiB,
2259 .line_size = 64,
2260 .associativity = 8,
2261 .partitions = 1,
2262 .sets = 1024,
2263 .lines_per_tag = 1,
2264 .self_init = true,
2265 .inclusive = true,
2266 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2267 },
2268 .l3_cache = &(CPUCacheInfo) {
2269 .type = UNIFIED_CACHE,
2270 .level = 3,
2271 .size = 8 * MiB,
2272 .line_size = 64,
2273 .associativity = 16,
2274 .partitions = 1,
2275 .sets = 8192,
2276 .lines_per_tag = 1,
2277 .self_init = true,
2278 .no_invd_sharing = true,
2279 .complex_indexing = false,
2280 .share_level = CPU_TOPOLOGY_LEVEL_DIE,
2281 },
2282 };
2283
2284 static const CPUCaches epyc_rome_cache_info = {
2285 .l1d_cache = &(CPUCacheInfo) {
2286 .type = DATA_CACHE,
2287 .level = 1,
2288 .size = 32 * KiB,
2289 .line_size = 64,
2290 .associativity = 8,
2291 .partitions = 1,
2292 .sets = 64,
2293 .lines_per_tag = 1,
2294 .self_init = 1,
2295 .no_invd_sharing = true,
2296 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2297 },
2298 .l1i_cache = &(CPUCacheInfo) {
2299 .type = INSTRUCTION_CACHE,
2300 .level = 1,
2301 .size = 32 * KiB,
2302 .line_size = 64,
2303 .associativity = 8,
2304 .partitions = 1,
2305 .sets = 64,
2306 .lines_per_tag = 1,
2307 .self_init = 1,
2308 .no_invd_sharing = true,
2309 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2310 },
2311 .l2_cache = &(CPUCacheInfo) {
2312 .type = UNIFIED_CACHE,
2313 .level = 2,
2314 .size = 512 * KiB,
2315 .line_size = 64,
2316 .associativity = 8,
2317 .partitions = 1,
2318 .sets = 1024,
2319 .lines_per_tag = 1,
2320 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2321 },
2322 .l3_cache = &(CPUCacheInfo) {
2323 .type = UNIFIED_CACHE,
2324 .level = 3,
2325 .size = 16 * MiB,
2326 .line_size = 64,
2327 .associativity = 16,
2328 .partitions = 1,
2329 .sets = 16384,
2330 .lines_per_tag = 1,
2331 .self_init = true,
2332 .inclusive = true,
2333 .complex_indexing = true,
2334 .share_level = CPU_TOPOLOGY_LEVEL_DIE,
2335 },
2336 };
2337
2338 static const CPUCaches epyc_rome_v3_cache_info = {
2339 .l1d_cache = &(CPUCacheInfo) {
2340 .type = DATA_CACHE,
2341 .level = 1,
2342 .size = 32 * KiB,
2343 .line_size = 64,
2344 .associativity = 8,
2345 .partitions = 1,
2346 .sets = 64,
2347 .lines_per_tag = 1,
2348 .self_init = 1,
2349 .no_invd_sharing = true,
2350 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2351 },
2352 .l1i_cache = &(CPUCacheInfo) {
2353 .type = INSTRUCTION_CACHE,
2354 .level = 1,
2355 .size = 32 * KiB,
2356 .line_size = 64,
2357 .associativity = 8,
2358 .partitions = 1,
2359 .sets = 64,
2360 .lines_per_tag = 1,
2361 .self_init = 1,
2362 .no_invd_sharing = true,
2363 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2364 },
2365 .l2_cache = &(CPUCacheInfo) {
2366 .type = UNIFIED_CACHE,
2367 .level = 2,
2368 .size = 512 * KiB,
2369 .line_size = 64,
2370 .associativity = 8,
2371 .partitions = 1,
2372 .sets = 1024,
2373 .lines_per_tag = 1,
2374 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2375 },
2376 .l3_cache = &(CPUCacheInfo) {
2377 .type = UNIFIED_CACHE,
2378 .level = 3,
2379 .size = 16 * MiB,
2380 .line_size = 64,
2381 .associativity = 16,
2382 .partitions = 1,
2383 .sets = 16384,
2384 .lines_per_tag = 1,
2385 .self_init = true,
2386 .inclusive = true,
2387 .complex_indexing = false,
2388 .share_level = CPU_TOPOLOGY_LEVEL_DIE,
2389 },
2390 };
2391
2392 static const CPUCaches epyc_rome_v5_cache_info = {
2393 .l1d_cache = &(CPUCacheInfo) {
2394 .type = DATA_CACHE,
2395 .level = 1,
2396 .size = 32 * KiB,
2397 .line_size = 64,
2398 .associativity = 8,
2399 .partitions = 1,
2400 .sets = 64,
2401 .lines_per_tag = 1,
2402 .self_init = true,
2403 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2404 },
2405 .l1i_cache = &(CPUCacheInfo) {
2406 .type = INSTRUCTION_CACHE,
2407 .level = 1,
2408 .size = 32 * KiB,
2409 .line_size = 64,
2410 .associativity = 8,
2411 .partitions = 1,
2412 .sets = 64,
2413 .lines_per_tag = 1,
2414 .self_init = true,
2415 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2416 },
2417 .l2_cache = &(CPUCacheInfo) {
2418 .type = UNIFIED_CACHE,
2419 .level = 2,
2420 .size = 512 * KiB,
2421 .line_size = 64,
2422 .associativity = 8,
2423 .partitions = 1,
2424 .sets = 1024,
2425 .lines_per_tag = 1,
2426 .self_init = true,
2427 .inclusive = true,
2428 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2429 },
2430 .l3_cache = &(CPUCacheInfo) {
2431 .type = UNIFIED_CACHE,
2432 .level = 3,
2433 .size = 16 * MiB,
2434 .line_size = 64,
2435 .associativity = 16,
2436 .partitions = 1,
2437 .sets = 16384,
2438 .lines_per_tag = 1,
2439 .self_init = true,
2440 .no_invd_sharing = true,
2441 .complex_indexing = false,
2442 .share_level = CPU_TOPOLOGY_LEVEL_DIE,
2443 },
2444 };
2445
2446 static const CPUCaches epyc_milan_cache_info = {
2447 .l1d_cache = &(CPUCacheInfo) {
2448 .type = DATA_CACHE,
2449 .level = 1,
2450 .size = 32 * KiB,
2451 .line_size = 64,
2452 .associativity = 8,
2453 .partitions = 1,
2454 .sets = 64,
2455 .lines_per_tag = 1,
2456 .self_init = 1,
2457 .no_invd_sharing = true,
2458 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2459 },
2460 .l1i_cache = &(CPUCacheInfo) {
2461 .type = INSTRUCTION_CACHE,
2462 .level = 1,
2463 .size = 32 * KiB,
2464 .line_size = 64,
2465 .associativity = 8,
2466 .partitions = 1,
2467 .sets = 64,
2468 .lines_per_tag = 1,
2469 .self_init = 1,
2470 .no_invd_sharing = true,
2471 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2472 },
2473 .l2_cache = &(CPUCacheInfo) {
2474 .type = UNIFIED_CACHE,
2475 .level = 2,
2476 .size = 512 * KiB,
2477 .line_size = 64,
2478 .associativity = 8,
2479 .partitions = 1,
2480 .sets = 1024,
2481 .lines_per_tag = 1,
2482 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2483 },
2484 .l3_cache = &(CPUCacheInfo) {
2485 .type = UNIFIED_CACHE,
2486 .level = 3,
2487 .size = 32 * MiB,
2488 .line_size = 64,
2489 .associativity = 16,
2490 .partitions = 1,
2491 .sets = 32768,
2492 .lines_per_tag = 1,
2493 .self_init = true,
2494 .inclusive = true,
2495 .complex_indexing = true,
2496 .share_level = CPU_TOPOLOGY_LEVEL_DIE,
2497 },
2498 };
2499
2500 static const CPUCaches epyc_milan_v2_cache_info = {
2501 .l1d_cache = &(CPUCacheInfo) {
2502 .type = DATA_CACHE,
2503 .level = 1,
2504 .size = 32 * KiB,
2505 .line_size = 64,
2506 .associativity = 8,
2507 .partitions = 1,
2508 .sets = 64,
2509 .lines_per_tag = 1,
2510 .self_init = 1,
2511 .no_invd_sharing = true,
2512 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2513 },
2514 .l1i_cache = &(CPUCacheInfo) {
2515 .type = INSTRUCTION_CACHE,
2516 .level = 1,
2517 .size = 32 * KiB,
2518 .line_size = 64,
2519 .associativity = 8,
2520 .partitions = 1,
2521 .sets = 64,
2522 .lines_per_tag = 1,
2523 .self_init = 1,
2524 .no_invd_sharing = true,
2525 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2526 },
2527 .l2_cache = &(CPUCacheInfo) {
2528 .type = UNIFIED_CACHE,
2529 .level = 2,
2530 .size = 512 * KiB,
2531 .line_size = 64,
2532 .associativity = 8,
2533 .partitions = 1,
2534 .sets = 1024,
2535 .lines_per_tag = 1,
2536 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2537 },
2538 .l3_cache = &(CPUCacheInfo) {
2539 .type = UNIFIED_CACHE,
2540 .level = 3,
2541 .size = 32 * MiB,
2542 .line_size = 64,
2543 .associativity = 16,
2544 .partitions = 1,
2545 .sets = 32768,
2546 .lines_per_tag = 1,
2547 .self_init = true,
2548 .inclusive = true,
2549 .complex_indexing = false,
2550 .share_level = CPU_TOPOLOGY_LEVEL_DIE,
2551 },
2552 };
2553
2554 static const CPUCaches epyc_milan_v3_cache_info = {
2555 .l1d_cache = &(CPUCacheInfo) {
2556 .type = DATA_CACHE,
2557 .level = 1,
2558 .size = 32 * KiB,
2559 .line_size = 64,
2560 .associativity = 8,
2561 .partitions = 1,
2562 .sets = 64,
2563 .lines_per_tag = 1,
2564 .self_init = true,
2565 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2566 },
2567 .l1i_cache = &(CPUCacheInfo) {
2568 .type = INSTRUCTION_CACHE,
2569 .level = 1,
2570 .size = 32 * KiB,
2571 .line_size = 64,
2572 .associativity = 8,
2573 .partitions = 1,
2574 .sets = 64,
2575 .lines_per_tag = 1,
2576 .self_init = true,
2577 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2578 },
2579 .l2_cache = &(CPUCacheInfo) {
2580 .type = UNIFIED_CACHE,
2581 .level = 2,
2582 .size = 512 * KiB,
2583 .line_size = 64,
2584 .associativity = 8,
2585 .partitions = 1,
2586 .sets = 1024,
2587 .lines_per_tag = 1,
2588 .self_init = true,
2589 .inclusive = true,
2590 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2591 },
2592 .l3_cache = &(CPUCacheInfo) {
2593 .type = UNIFIED_CACHE,
2594 .level = 3,
2595 .size = 32 * MiB,
2596 .line_size = 64,
2597 .associativity = 16,
2598 .partitions = 1,
2599 .sets = 32768,
2600 .lines_per_tag = 1,
2601 .self_init = true,
2602 .no_invd_sharing = true,
2603 .complex_indexing = false,
2604 .share_level = CPU_TOPOLOGY_LEVEL_DIE,
2605 },
2606 };
2607
2608 static const CPUCaches epyc_genoa_cache_info = {
2609 .l1d_cache = &(CPUCacheInfo) {
2610 .type = DATA_CACHE,
2611 .level = 1,
2612 .size = 32 * KiB,
2613 .line_size = 64,
2614 .associativity = 8,
2615 .partitions = 1,
2616 .sets = 64,
2617 .lines_per_tag = 1,
2618 .self_init = 1,
2619 .no_invd_sharing = true,
2620 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2621 },
2622 .l1i_cache = &(CPUCacheInfo) {
2623 .type = INSTRUCTION_CACHE,
2624 .level = 1,
2625 .size = 32 * KiB,
2626 .line_size = 64,
2627 .associativity = 8,
2628 .partitions = 1,
2629 .sets = 64,
2630 .lines_per_tag = 1,
2631 .self_init = 1,
2632 .no_invd_sharing = true,
2633 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2634 },
2635 .l2_cache = &(CPUCacheInfo) {
2636 .type = UNIFIED_CACHE,
2637 .level = 2,
2638 .size = 1 * MiB,
2639 .line_size = 64,
2640 .associativity = 8,
2641 .partitions = 1,
2642 .sets = 2048,
2643 .lines_per_tag = 1,
2644 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2645 },
2646 .l3_cache = &(CPUCacheInfo) {
2647 .type = UNIFIED_CACHE,
2648 .level = 3,
2649 .size = 32 * MiB,
2650 .line_size = 64,
2651 .associativity = 16,
2652 .partitions = 1,
2653 .sets = 32768,
2654 .lines_per_tag = 1,
2655 .self_init = true,
2656 .inclusive = true,
2657 .complex_indexing = false,
2658 .share_level = CPU_TOPOLOGY_LEVEL_DIE,
2659 },
2660 };
2661
2662 static const CPUCaches epyc_genoa_v2_cache_info = {
2663 .l1d_cache = &(CPUCacheInfo) {
2664 .type = DATA_CACHE,
2665 .level = 1,
2666 .size = 32 * KiB,
2667 .line_size = 64,
2668 .associativity = 8,
2669 .partitions = 1,
2670 .sets = 64,
2671 .lines_per_tag = 1,
2672 .self_init = true,
2673 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2674 },
2675 .l1i_cache = &(CPUCacheInfo) {
2676 .type = INSTRUCTION_CACHE,
2677 .level = 1,
2678 .size = 32 * KiB,
2679 .line_size = 64,
2680 .associativity = 8,
2681 .partitions = 1,
2682 .sets = 64,
2683 .lines_per_tag = 1,
2684 .self_init = true,
2685 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2686 },
2687 .l2_cache = &(CPUCacheInfo) {
2688 .type = UNIFIED_CACHE,
2689 .level = 2,
2690 .size = 1 * MiB,
2691 .line_size = 64,
2692 .associativity = 8,
2693 .partitions = 1,
2694 .sets = 2048,
2695 .lines_per_tag = 1,
2696 .self_init = true,
2697 .inclusive = true,
2698 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2699 },
2700 .l3_cache = &(CPUCacheInfo) {
2701 .type = UNIFIED_CACHE,
2702 .level = 3,
2703 .size = 32 * MiB,
2704 .line_size = 64,
2705 .associativity = 16,
2706 .partitions = 1,
2707 .sets = 32768,
2708 .lines_per_tag = 1,
2709 .self_init = true,
2710 .no_invd_sharing = true,
2711 .complex_indexing = false,
2712 .share_level = CPU_TOPOLOGY_LEVEL_DIE,
2713 },
2714 };
2715
2716 static const CPUCaches epyc_turin_cache_info = {
2717 .l1d_cache = &(CPUCacheInfo) {
2718 .type = DATA_CACHE,
2719 .level = 1,
2720 .size = 48 * KiB,
2721 .line_size = 64,
2722 .associativity = 12,
2723 .partitions = 1,
2724 .sets = 64,
2725 .lines_per_tag = 1,
2726 .self_init = true,
2727 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2728 },
2729 .l1i_cache = &(CPUCacheInfo) {
2730 .type = INSTRUCTION_CACHE,
2731 .level = 1,
2732 .size = 32 * KiB,
2733 .line_size = 64,
2734 .associativity = 8,
2735 .partitions = 1,
2736 .sets = 64,
2737 .lines_per_tag = 1,
2738 .self_init = true,
2739 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2740 },
2741 .l2_cache = &(CPUCacheInfo) {
2742 .type = UNIFIED_CACHE,
2743 .level = 2,
2744 .size = 1 * MiB,
2745 .line_size = 64,
2746 .associativity = 16,
2747 .partitions = 1,
2748 .sets = 1024,
2749 .lines_per_tag = 1,
2750 .self_init = true,
2751 .inclusive = true,
2752 .share_level = CPU_TOPOLOGY_LEVEL_CORE,
2753 },
2754 .l3_cache = &(CPUCacheInfo) {
2755 .type = UNIFIED_CACHE,
2756 .level = 3,
2757 .size = 32 * MiB,
2758 .line_size = 64,
2759 .associativity = 16,
2760 .partitions = 1,
2761 .sets = 32768,
2762 .lines_per_tag = 1,
2763 .self_init = true,
2764 .no_invd_sharing = true,
2765 .complex_indexing = false,
2766 .share_level = CPU_TOPOLOGY_LEVEL_DIE,
2767 },
2768 };
2769
2770 /* The following VMX features are not supported by KVM and are left out in the
2771 * CPU definitions:
2772 *
2773 * Dual-monitor support (all processors)
2774 * Entry to SMM
2775 * Deactivate dual-monitor treatment
2776 * Number of CR3-target values
2777 * Shutdown activity state
2778 * Wait-for-SIPI activity state
2779 * PAUSE-loop exiting (Westmere and newer)
2780 * EPT-violation #VE (Broadwell and newer)
2781 * Inject event with insn length=0 (Skylake and newer)
2782 * Conceal non-root operation from PT
2783 * Conceal VM exits from PT
2784 * Conceal VM entries from PT
2785 * Enable ENCLS exiting
2786 * Mode-based execute control (XS/XU)
2787 * TSC scaling (Skylake Server and newer)
2788 * GPA translation for PT (IceLake and newer)
2789 * User wait and pause
2790 * ENCLV exiting
2791 * Load IA32_RTIT_CTL
2792 * Clear IA32_RTIT_CTL
2793 * Advanced VM-exit information for EPT violations
2794 * Sub-page write permissions
2795 * PT in VMX operation
2796 */
2797
2798 static const X86CPUDefinition builtin_x86_defs[] = {
2799 {
2800 .name = "qemu64",
2801 .level = 0xd,
2802 .vendor = CPUID_VENDOR_AMD,
2803 .family = 15,
2804 .model = 107,
2805 .stepping = 1,
2806 .features[FEAT_1_EDX] =
2807 PPRO_FEATURES |
2808 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
2809 CPUID_PSE36,
2810 .features[FEAT_1_ECX] =
2811 CPUID_EXT_SSE3 | CPUID_EXT_CX16,
2812 .features[FEAT_8000_0001_EDX] =
2813 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
2814 .features[FEAT_8000_0001_ECX] =
2815 CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM,
2816 .xlevel = 0x8000000A,
2817 .model_id = "QEMU Virtual CPU version " QEMU_HW_VERSION,
2818 },
2819 {
2820 .name = "phenom",
2821 .level = 5,
2822 .vendor = CPUID_VENDOR_AMD,
2823 .family = 16,
2824 .model = 2,
2825 .stepping = 3,
2826 /* Missing: CPUID_HT */
2827 .features[FEAT_1_EDX] =
2828 PPRO_FEATURES |
2829 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
2830 CPUID_PSE36 | CPUID_VME,
2831 .features[FEAT_1_ECX] =
2832 CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_CX16 |
2833 CPUID_EXT_POPCNT,
2834 .features[FEAT_8000_0001_EDX] =
2835 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX |
2836 CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT | CPUID_EXT2_MMXEXT |
2837 CPUID_EXT2_FFXSR | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP,
2838 /* Missing: CPUID_EXT3_CMP_LEG, CPUID_EXT3_EXTAPIC,
2839 CPUID_EXT3_CR8LEG,
2840 CPUID_EXT3_MISALIGNSSE, CPUID_EXT3_3DNOWPREFETCH,
2841 CPUID_EXT3_OSVW, CPUID_EXT3_IBS */
2842 .features[FEAT_8000_0001_ECX] =
2843 CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM |
2844 CPUID_EXT3_ABM | CPUID_EXT3_SSE4A,
2845 /* Missing: CPUID_SVM_LBRV */
2846 .features[FEAT_SVM] =
2847 CPUID_SVM_NPT,
2848 .xlevel = 0x8000001A,
2849 .model_id = "AMD Phenom(tm) 9550 Quad-Core Processor"
2850 },
2851 {
2852 .name = "core2duo",
2853 .level = 10,
2854 .vendor = CPUID_VENDOR_INTEL,
2855 .family = 6,
2856 .model = 15,
2857 .stepping = 11,
2858 /* Missing: CPUID_DTS, CPUID_HT, CPUID_TM, CPUID_PBE */
2859 .features[FEAT_1_EDX] =
2860 PPRO_FEATURES |
2861 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
2862 CPUID_PSE36 | CPUID_VME | CPUID_ACPI | CPUID_SS,
2863 /* Missing: CPUID_EXT_DTES64, CPUID_EXT_DSCPL, CPUID_EXT_EST,
2864 * CPUID_EXT_TM2, CPUID_EXT_XTPR, CPUID_EXT_PDCM, CPUID_EXT_VMX */
2865 .features[FEAT_1_ECX] =
2866 CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_SSSE3 |
2867 CPUID_EXT_CX16,
2868 .features[FEAT_8000_0001_EDX] =
2869 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
2870 .features[FEAT_8000_0001_ECX] =
2871 CPUID_EXT3_LAHF_LM,
2872 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS,
2873 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
2874 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
2875 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
2876 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2877 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS,
2878 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2879 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2880 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2881 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2882 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2883 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2884 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2885 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2886 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2887 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2888 .features[FEAT_VMX_SECONDARY_CTLS] =
2889 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES,
2890 .xlevel = 0x80000008,
2891 .model_id = "Intel(R) Core(TM)2 Duo CPU T7700 @ 2.40GHz",
2892 },
2893 {
2894 .name = "kvm64",
2895 .level = 0xd,
2896 .vendor = CPUID_VENDOR_INTEL,
2897 .family = 15,
2898 .model = 6,
2899 .stepping = 1,
2900 /* Missing: CPUID_HT */
2901 .features[FEAT_1_EDX] =
2902 PPRO_FEATURES | CPUID_VME |
2903 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
2904 CPUID_PSE36,
2905 /* Missing: CPUID_EXT_POPCNT, CPUID_EXT_MONITOR */
2906 .features[FEAT_1_ECX] =
2907 CPUID_EXT_SSE3 | CPUID_EXT_CX16,
2908 /* Missing: CPUID_EXT2_PDPE1GB, CPUID_EXT2_RDTSCP */
2909 .features[FEAT_8000_0001_EDX] =
2910 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
2911 /* Missing: CPUID_EXT3_LAHF_LM, CPUID_EXT3_CMP_LEG, CPUID_EXT3_EXTAPIC,
2912 CPUID_EXT3_CR8LEG, CPUID_EXT3_ABM, CPUID_EXT3_SSE4A,
2913 CPUID_EXT3_MISALIGNSSE, CPUID_EXT3_3DNOWPREFETCH,
2914 CPUID_EXT3_OSVW, CPUID_EXT3_IBS, CPUID_EXT3_SVM */
2915 .features[FEAT_8000_0001_ECX] =
2916 0,
2917 /* VMX features from Cedar Mill/Prescott */
2918 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
2919 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
2920 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
2921 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2922 VMX_PIN_BASED_NMI_EXITING,
2923 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2924 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2925 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2926 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2927 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2928 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2929 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2930 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING,
2931 .xlevel = 0x80000008,
2932 .model_id = "Common KVM processor"
2933 },
2934 {
2935 .name = "qemu32",
2936 .level = 4,
2937 .vendor = CPUID_VENDOR_INTEL,
2938 .family = 6,
2939 .model = 6,
2940 .stepping = 3,
2941 .features[FEAT_1_EDX] =
2942 PPRO_FEATURES,
2943 .features[FEAT_1_ECX] =
2944 CPUID_EXT_SSE3,
2945 .xlevel = 0x80000004,
2946 .model_id = "QEMU Virtual CPU version " QEMU_HW_VERSION,
2947 },
2948 {
2949 .name = "kvm32",
2950 .level = 5,
2951 .vendor = CPUID_VENDOR_INTEL,
2952 .family = 15,
2953 .model = 6,
2954 .stepping = 1,
2955 .features[FEAT_1_EDX] =
2956 PPRO_FEATURES | CPUID_VME |
2957 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_PSE36,
2958 .features[FEAT_1_ECX] =
2959 CPUID_EXT_SSE3,
2960 .features[FEAT_8000_0001_ECX] =
2961 0,
2962 /* VMX features from Yonah */
2963 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
2964 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
2965 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
2966 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2967 VMX_PIN_BASED_NMI_EXITING,
2968 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2969 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2970 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2971 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2972 VMX_CPU_BASED_MOV_DR_EXITING | VMX_CPU_BASED_UNCOND_IO_EXITING |
2973 VMX_CPU_BASED_USE_IO_BITMAPS | VMX_CPU_BASED_MONITOR_EXITING |
2974 VMX_CPU_BASED_PAUSE_EXITING | VMX_CPU_BASED_USE_MSR_BITMAPS,
2975 .xlevel = 0x80000008,
2976 .model_id = "Common 32-bit KVM processor"
2977 },
2978 {
2979 .name = "coreduo",
2980 .level = 10,
2981 .vendor = CPUID_VENDOR_INTEL,
2982 .family = 6,
2983 .model = 14,
2984 .stepping = 8,
2985 /* Missing: CPUID_DTS, CPUID_HT, CPUID_TM, CPUID_PBE */
2986 .features[FEAT_1_EDX] =
2987 PPRO_FEATURES | CPUID_VME |
2988 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_ACPI |
2989 CPUID_SS,
2990 /* Missing: CPUID_EXT_EST, CPUID_EXT_TM2 , CPUID_EXT_XTPR,
2991 * CPUID_EXT_PDCM, CPUID_EXT_VMX */
2992 .features[FEAT_1_ECX] =
2993 CPUID_EXT_SSE3 | CPUID_EXT_MONITOR,
2994 .features[FEAT_8000_0001_EDX] =
2995 CPUID_EXT2_NX,
2996 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
2997 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
2998 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
2999 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3000 VMX_PIN_BASED_NMI_EXITING,
3001 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3002 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3003 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3004 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3005 VMX_CPU_BASED_MOV_DR_EXITING | VMX_CPU_BASED_UNCOND_IO_EXITING |
3006 VMX_CPU_BASED_USE_IO_BITMAPS | VMX_CPU_BASED_MONITOR_EXITING |
3007 VMX_CPU_BASED_PAUSE_EXITING | VMX_CPU_BASED_USE_MSR_BITMAPS,
3008 .xlevel = 0x80000008,
3009 .model_id = "Genuine Intel(R) CPU T2600 @ 2.16GHz",
3010 },
3011 {
3012 .name = "486",
3013 .level = 1,
3014 .vendor = CPUID_VENDOR_INTEL,
3015 .family = 4,
3016 .model = 8,
3017 .stepping = 0,
3018 .features[FEAT_1_EDX] =
3019 I486_FEATURES,
3020 .xlevel = 0,
3021 .model_id = "",
3022 },
3023 {
3024 .name = "pentium",
3025 .level = 1,
3026 .vendor = CPUID_VENDOR_INTEL,
3027 .family = 5,
3028 .model = 4,
3029 .stepping = 3,
3030 .features[FEAT_1_EDX] =
3031 PENTIUM_FEATURES,
3032 .xlevel = 0,
3033 .model_id = "",
3034 },
3035 {
3036 .name = "pentium2",
3037 .level = 2,
3038 .vendor = CPUID_VENDOR_INTEL,
3039 .family = 6,
3040 .model = 5,
3041 .stepping = 2,
3042 .features[FEAT_1_EDX] =
3043 PENTIUM2_FEATURES,
3044 .xlevel = 0,
3045 .model_id = "",
3046 },
3047 {
3048 .name = "pentium3",
3049 .level = 3,
3050 .vendor = CPUID_VENDOR_INTEL,
3051 .family = 6,
3052 .model = 7,
3053 .stepping = 3,
3054 .features[FEAT_1_EDX] =
3055 PENTIUM3_FEATURES,
3056 .xlevel = 0,
3057 .model_id = "",
3058 },
3059 {
3060 .name = "athlon",
3061 .level = 2,
3062 .vendor = CPUID_VENDOR_AMD,
3063 .family = 6,
3064 .model = 2,
3065 .stepping = 3,
3066 .features[FEAT_1_EDX] =
3067 PPRO_FEATURES | CPUID_PSE36 | CPUID_VME | CPUID_MTRR |
3068 CPUID_MCA,
3069 .features[FEAT_8000_0001_EDX] =
3070 CPUID_EXT2_MMXEXT | CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT,
3071 .xlevel = 0x80000008,
3072 .model_id = "QEMU Virtual CPU version " QEMU_HW_VERSION,
3073 },
3074 {
3075 .name = "n270",
3076 .level = 10,
3077 .vendor = CPUID_VENDOR_INTEL,
3078 .family = 6,
3079 .model = 28,
3080 .stepping = 2,
3081 /* Missing: CPUID_DTS, CPUID_HT, CPUID_TM, CPUID_PBE */
3082 .features[FEAT_1_EDX] =
3083 PPRO_FEATURES |
3084 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_VME |
3085 CPUID_ACPI | CPUID_SS,
3086 /* Some CPUs got no CPUID_SEP */
3087 /* Missing: CPUID_EXT_DSCPL, CPUID_EXT_EST, CPUID_EXT_TM2,
3088 * CPUID_EXT_XTPR */
3089 .features[FEAT_1_ECX] =
3090 CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_SSSE3 |
3091 CPUID_EXT_MOVBE,
3092 .features[FEAT_8000_0001_EDX] =
3093 CPUID_EXT2_NX,
3094 .features[FEAT_8000_0001_ECX] =
3095 CPUID_EXT3_LAHF_LM,
3096 .xlevel = 0x80000008,
3097 .model_id = "Intel(R) Atom(TM) CPU N270 @ 1.60GHz",
3098 },
3099 {
3100 .name = "Conroe",
3101 .level = 10,
3102 .vendor = CPUID_VENDOR_INTEL,
3103 .family = 6,
3104 .model = 15,
3105 .stepping = 3,
3106 .features[FEAT_1_EDX] =
3107 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3108 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3109 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3110 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3111 CPUID_DE | CPUID_FP87,
3112 .features[FEAT_1_ECX] =
3113 CPUID_EXT_SSSE3 | CPUID_EXT_SSE3,
3114 .features[FEAT_8000_0001_EDX] =
3115 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3116 .features[FEAT_8000_0001_ECX] =
3117 CPUID_EXT3_LAHF_LM,
3118 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS,
3119 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
3120 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
3121 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
3122 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3123 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS,
3124 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3125 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3126 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3127 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3128 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3129 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3130 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3131 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3132 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3133 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3134 .features[FEAT_VMX_SECONDARY_CTLS] =
3135 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES,
3136 .xlevel = 0x80000008,
3137 .model_id = "Intel Celeron_4x0 (Conroe/Merom Class Core 2)",
3138 },
3139 {
3140 .name = "Penryn",
3141 .level = 10,
3142 .vendor = CPUID_VENDOR_INTEL,
3143 .family = 6,
3144 .model = 23,
3145 .stepping = 3,
3146 .features[FEAT_1_EDX] =
3147 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3148 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3149 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3150 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3151 CPUID_DE | CPUID_FP87,
3152 .features[FEAT_1_ECX] =
3153 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3154 CPUID_EXT_SSE3,
3155 .features[FEAT_8000_0001_EDX] =
3156 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3157 .features[FEAT_8000_0001_ECX] =
3158 CPUID_EXT3_LAHF_LM,
3159 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS,
3160 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3161 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL,
3162 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT |
3163 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL,
3164 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
3165 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3166 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS,
3167 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3168 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3169 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3170 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3171 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3172 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3173 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3174 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3175 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3176 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3177 .features[FEAT_VMX_SECONDARY_CTLS] =
3178 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3179 VMX_SECONDARY_EXEC_WBINVD_EXITING,
3180 .xlevel = 0x80000008,
3181 .model_id = "Intel Core 2 Duo P9xxx (Penryn Class Core 2)",
3182 },
3183 {
3184 .name = "Nehalem",
3185 .level = 11,
3186 .vendor = CPUID_VENDOR_INTEL,
3187 .family = 6,
3188 .model = 26,
3189 .stepping = 3,
3190 .features[FEAT_1_EDX] =
3191 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3192 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3193 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3194 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3195 CPUID_DE | CPUID_FP87,
3196 .features[FEAT_1_ECX] =
3197 CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
3198 CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_SSE3,
3199 .features[FEAT_8000_0001_EDX] =
3200 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
3201 .features[FEAT_8000_0001_ECX] =
3202 CPUID_EXT3_LAHF_LM,
3203 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3204 MSR_VMX_BASIC_TRUE_CTLS,
3205 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3206 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3207 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3208 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3209 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3210 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3211 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3212 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3213 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3214 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
3215 .features[FEAT_VMX_EXIT_CTLS] =
3216 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3217 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3218 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3219 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3220 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3221 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
3222 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3223 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3224 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
3225 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3226 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3227 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3228 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3229 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3230 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3231 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3232 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3233 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3234 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3235 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3236 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3237 .features[FEAT_VMX_SECONDARY_CTLS] =
3238 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3239 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3240 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3241 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3242 VMX_SECONDARY_EXEC_ENABLE_VPID,
3243 .xlevel = 0x80000008,
3244 .model_id = "Intel Core i7 9xx (Nehalem Class Core i7)",
3245 .versions = (X86CPUVersionDefinition[]) {
3246 { .version = 1 },
3247 {
3248 .version = 2,
3249 .alias = "Nehalem-IBRS",
3250 .props = (PropValue[]) {
3251 { "spec-ctrl", "on" },
3252 { "model-id",
3253 "Intel Core i7 9xx (Nehalem Core i7, IBRS update)" },
3254 { /* end of list */ }
3255 }
3256 },
3257 { /* end of list */ }
3258 }
3259 },
3260 {
3261 .name = "Westmere",
3262 .level = 11,
3263 .vendor = CPUID_VENDOR_INTEL,
3264 .family = 6,
3265 .model = 44,
3266 .stepping = 1,
3267 .features[FEAT_1_EDX] =
3268 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3269 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3270 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3271 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3272 CPUID_DE | CPUID_FP87,
3273 .features[FEAT_1_ECX] =
3274 CPUID_EXT_AES | CPUID_EXT_POPCNT | CPUID_EXT_SSE42 |
3275 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3276 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3,
3277 .features[FEAT_8000_0001_EDX] =
3278 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
3279 .features[FEAT_8000_0001_ECX] =
3280 CPUID_EXT3_LAHF_LM,
3281 .features[FEAT_6_EAX] =
3282 CPUID_6_EAX_ARAT,
3283 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3284 MSR_VMX_BASIC_TRUE_CTLS,
3285 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3286 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3287 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3288 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3289 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3290 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3291 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3292 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3293 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3294 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
3295 .features[FEAT_VMX_EXIT_CTLS] =
3296 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3297 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3298 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3299 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3300 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3301 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3302 MSR_VMX_MISC_STORE_LMA,
3303 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3304 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3305 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
3306 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3307 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3308 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3309 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3310 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3311 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3312 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3313 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3314 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3315 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3316 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3317 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3318 .features[FEAT_VMX_SECONDARY_CTLS] =
3319 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3320 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3321 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3322 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3323 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST,
3324 .xlevel = 0x80000008,
3325 .model_id = "Westmere E56xx/L56xx/X56xx (Nehalem-C)",
3326 .versions = (X86CPUVersionDefinition[]) {
3327 { .version = 1 },
3328 {
3329 .version = 2,
3330 .alias = "Westmere-IBRS",
3331 .props = (PropValue[]) {
3332 { "spec-ctrl", "on" },
3333 { "model-id",
3334 "Westmere E56xx/L56xx/X56xx (IBRS update)" },
3335 { /* end of list */ }
3336 }
3337 },
3338 { /* end of list */ }
3339 }
3340 },
3341 {
3342 .name = "SandyBridge",
3343 .level = 0xd,
3344 .vendor = CPUID_VENDOR_INTEL,
3345 .family = 6,
3346 .model = 42,
3347 .stepping = 1,
3348 .features[FEAT_1_EDX] =
3349 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3350 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3351 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3352 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3353 CPUID_DE | CPUID_FP87,
3354 .features[FEAT_1_ECX] =
3355 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3356 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_POPCNT |
3357 CPUID_EXT_X2APIC | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
3358 CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ |
3359 CPUID_EXT_SSE3,
3360 .features[FEAT_8000_0001_EDX] =
3361 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
3362 CPUID_EXT2_SYSCALL,
3363 .features[FEAT_8000_0001_ECX] =
3364 CPUID_EXT3_LAHF_LM,
3365 .features[FEAT_XSAVE] =
3366 CPUID_XSAVE_XSAVEOPT,
3367 .features[FEAT_6_EAX] =
3368 CPUID_6_EAX_ARAT,
3369 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3370 MSR_VMX_BASIC_TRUE_CTLS,
3371 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3372 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3373 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3374 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3375 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3376 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3377 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3378 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3379 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3380 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
3381 .features[FEAT_VMX_EXIT_CTLS] =
3382 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3383 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3384 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3385 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3386 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3387 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3388 MSR_VMX_MISC_STORE_LMA,
3389 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3390 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3391 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
3392 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3393 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3394 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3395 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3396 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3397 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3398 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3399 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3400 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3401 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3402 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3403 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3404 .features[FEAT_VMX_SECONDARY_CTLS] =
3405 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3406 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3407 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3408 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3409 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST,
3410 .xlevel = 0x80000008,
3411 .model_id = "Intel Xeon E312xx (Sandy Bridge)",
3412 .versions = (X86CPUVersionDefinition[]) {
3413 { .version = 1 },
3414 {
3415 .version = 2,
3416 .alias = "SandyBridge-IBRS",
3417 .props = (PropValue[]) {
3418 { "spec-ctrl", "on" },
3419 { "model-id",
3420 "Intel Xeon E312xx (Sandy Bridge, IBRS update)" },
3421 { /* end of list */ }
3422 }
3423 },
3424 { /* end of list */ }
3425 }
3426 },
3427 {
3428 .name = "IvyBridge",
3429 .level = 0xd,
3430 .vendor = CPUID_VENDOR_INTEL,
3431 .family = 6,
3432 .model = 58,
3433 .stepping = 9,
3434 .features[FEAT_1_EDX] =
3435 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3436 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3437 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3438 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3439 CPUID_DE | CPUID_FP87,
3440 .features[FEAT_1_ECX] =
3441 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3442 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_POPCNT |
3443 CPUID_EXT_X2APIC | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
3444 CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ |
3445 CPUID_EXT_SSE3 | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3446 .features[FEAT_7_0_EBX] =
3447 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_SMEP |
3448 CPUID_7_0_EBX_ERMS,
3449 .features[FEAT_8000_0001_EDX] =
3450 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
3451 CPUID_EXT2_SYSCALL,
3452 .features[FEAT_8000_0001_ECX] =
3453 CPUID_EXT3_LAHF_LM,
3454 .features[FEAT_XSAVE] =
3455 CPUID_XSAVE_XSAVEOPT,
3456 .features[FEAT_6_EAX] =
3457 CPUID_6_EAX_ARAT,
3458 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3459 MSR_VMX_BASIC_TRUE_CTLS,
3460 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3461 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3462 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3463 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3464 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3465 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3466 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3467 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3468 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3469 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
3470 .features[FEAT_VMX_EXIT_CTLS] =
3471 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3472 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3473 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3474 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3475 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3476 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3477 MSR_VMX_MISC_STORE_LMA,
3478 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3479 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3480 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3481 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3482 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3483 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3484 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3485 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3486 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3487 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3488 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3489 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3490 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3491 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3492 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3493 .features[FEAT_VMX_SECONDARY_CTLS] =
3494 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3495 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3496 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3497 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3498 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3499 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3500 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3501 VMX_SECONDARY_EXEC_RDRAND_EXITING,
3502 .xlevel = 0x80000008,
3503 .model_id = "Intel Xeon E3-12xx v2 (Ivy Bridge)",
3504 .versions = (X86CPUVersionDefinition[]) {
3505 { .version = 1 },
3506 {
3507 .version = 2,
3508 .alias = "IvyBridge-IBRS",
3509 .props = (PropValue[]) {
3510 { "spec-ctrl", "on" },
3511 { "model-id",
3512 "Intel Xeon E3-12xx v2 (Ivy Bridge, IBRS)" },
3513 { /* end of list */ }
3514 }
3515 },
3516 { /* end of list */ }
3517 }
3518 },
3519 {
3520 .name = "Haswell",
3521 .level = 0xd,
3522 .vendor = CPUID_VENDOR_INTEL,
3523 .family = 6,
3524 .model = 60,
3525 .stepping = 4,
3526 .features[FEAT_1_EDX] =
3527 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3528 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3529 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3530 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3531 CPUID_DE | CPUID_FP87,
3532 .features[FEAT_1_ECX] =
3533 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3534 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3535 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3536 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3537 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3538 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3539 .features[FEAT_8000_0001_EDX] =
3540 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
3541 CPUID_EXT2_SYSCALL,
3542 .features[FEAT_8000_0001_ECX] =
3543 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM,
3544 .features[FEAT_7_0_EBX] =
3545 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
3546 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
3547 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
3548 CPUID_7_0_EBX_RTM,
3549 .features[FEAT_XSAVE] =
3550 CPUID_XSAVE_XSAVEOPT,
3551 .features[FEAT_6_EAX] =
3552 CPUID_6_EAX_ARAT,
3553 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3554 MSR_VMX_BASIC_TRUE_CTLS,
3555 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3556 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3557 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3558 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3559 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3560 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3561 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3562 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3563 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3564 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3565 .features[FEAT_VMX_EXIT_CTLS] =
3566 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3567 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3568 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3569 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3570 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3571 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3572 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3573 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3574 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3575 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3576 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3577 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3578 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3579 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3580 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3581 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3582 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3583 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3584 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3585 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3586 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3587 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3588 .features[FEAT_VMX_SECONDARY_CTLS] =
3589 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3590 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3591 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3592 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3593 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3594 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3595 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3596 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3597 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS,
3598 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
3599 .xlevel = 0x80000008,
3600 .model_id = "Intel Core Processor (Haswell)",
3601 .versions = (X86CPUVersionDefinition[]) {
3602 { .version = 1 },
3603 {
3604 .version = 2,
3605 .alias = "Haswell-noTSX",
3606 .props = (PropValue[]) {
3607 { "hle", "off" },
3608 { "rtm", "off" },
3609 { "stepping", "1" },
3610 { "model-id", "Intel Core Processor (Haswell, no TSX)", },
3611 { /* end of list */ }
3612 },
3613 },
3614 {
3615 .version = 3,
3616 .alias = "Haswell-IBRS",
3617 .props = (PropValue[]) {
3618 /* Restore TSX features removed by -v2 above */
3619 { "hle", "on" },
3620 { "rtm", "on" },
3621 /*
3622 * Haswell and Haswell-IBRS had stepping=4 in
3623 * QEMU 4.0 and older
3624 */
3625 { "stepping", "4" },
3626 { "spec-ctrl", "on" },
3627 { "model-id",
3628 "Intel Core Processor (Haswell, IBRS)" },
3629 { /* end of list */ }
3630 }
3631 },
3632 {
3633 .version = 4,
3634 .alias = "Haswell-noTSX-IBRS",
3635 .props = (PropValue[]) {
3636 { "hle", "off" },
3637 { "rtm", "off" },
3638 /* spec-ctrl was already enabled by -v3 above */
3639 { "stepping", "1" },
3640 { "model-id",
3641 "Intel Core Processor (Haswell, no TSX, IBRS)" },
3642 { /* end of list */ }
3643 }
3644 },
3645 { /* end of list */ }
3646 }
3647 },
3648 {
3649 .name = "Broadwell",
3650 .level = 0xd,
3651 .vendor = CPUID_VENDOR_INTEL,
3652 .family = 6,
3653 .model = 61,
3654 .stepping = 2,
3655 .features[FEAT_1_EDX] =
3656 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3657 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3658 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3659 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3660 CPUID_DE | CPUID_FP87,
3661 .features[FEAT_1_ECX] =
3662 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3663 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3664 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3665 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3666 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3667 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3668 .features[FEAT_8000_0001_EDX] =
3669 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
3670 CPUID_EXT2_SYSCALL,
3671 .features[FEAT_8000_0001_ECX] =
3672 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3673 .features[FEAT_7_0_EBX] =
3674 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
3675 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
3676 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
3677 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
3678 CPUID_7_0_EBX_SMAP,
3679 .features[FEAT_XSAVE] =
3680 CPUID_XSAVE_XSAVEOPT,
3681 .features[FEAT_6_EAX] =
3682 CPUID_6_EAX_ARAT,
3683 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3684 MSR_VMX_BASIC_TRUE_CTLS,
3685 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3686 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3687 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3688 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3689 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3690 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3691 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3692 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3693 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3694 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3695 .features[FEAT_VMX_EXIT_CTLS] =
3696 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3697 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3698 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3699 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3700 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3701 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3702 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3703 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3704 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3705 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3706 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3707 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3708 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3709 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3710 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3711 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3712 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3713 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3714 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3715 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3716 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3717 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3718 .features[FEAT_VMX_SECONDARY_CTLS] =
3719 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3720 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3721 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3722 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3723 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3724 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3725 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3726 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3727 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3728 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3729 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
3730 .xlevel = 0x80000008,
3731 .model_id = "Intel Core Processor (Broadwell)",
3732 .versions = (X86CPUVersionDefinition[]) {
3733 { .version = 1 },
3734 {
3735 .version = 2,
3736 .alias = "Broadwell-noTSX",
3737 .props = (PropValue[]) {
3738 { "hle", "off" },
3739 { "rtm", "off" },
3740 { "model-id", "Intel Core Processor (Broadwell, no TSX)", },
3741 { /* end of list */ }
3742 },
3743 },
3744 {
3745 .version = 3,
3746 .alias = "Broadwell-IBRS",
3747 .props = (PropValue[]) {
3748 /* Restore TSX features removed by -v2 above */
3749 { "hle", "on" },
3750 { "rtm", "on" },
3751 { "spec-ctrl", "on" },
3752 { "model-id",
3753 "Intel Core Processor (Broadwell, IBRS)" },
3754 { /* end of list */ }
3755 }
3756 },
3757 {
3758 .version = 4,
3759 .alias = "Broadwell-noTSX-IBRS",
3760 .props = (PropValue[]) {
3761 { "hle", "off" },
3762 { "rtm", "off" },
3763 /* spec-ctrl was already enabled by -v3 above */
3764 { "model-id",
3765 "Intel Core Processor (Broadwell, no TSX, IBRS)" },
3766 { /* end of list */ }
3767 }
3768 },
3769 { /* end of list */ }
3770 }
3771 },
3772 {
3773 .name = "Skylake-Client",
3774 .level = 0xd,
3775 .vendor = CPUID_VENDOR_INTEL,
3776 .family = 6,
3777 .model = 94,
3778 .stepping = 3,
3779 .features[FEAT_1_EDX] =
3780 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3781 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3782 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3783 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3784 CPUID_DE | CPUID_FP87,
3785 .features[FEAT_1_ECX] =
3786 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3787 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3788 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3789 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3790 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3791 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3792 .features[FEAT_8000_0001_EDX] =
3793 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
3794 CPUID_EXT2_SYSCALL,
3795 .features[FEAT_8000_0001_ECX] =
3796 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3797 .features[FEAT_7_0_EBX] =
3798 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
3799 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
3800 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
3801 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
3802 CPUID_7_0_EBX_SMAP,
3803 /* XSAVES is added in version 4 */
3804 .features[FEAT_XSAVE] =
3805 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3806 CPUID_XSAVE_XGETBV1,
3807 .features[FEAT_6_EAX] =
3808 CPUID_6_EAX_ARAT,
3809 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
3810 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3811 MSR_VMX_BASIC_TRUE_CTLS,
3812 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3813 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3814 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3815 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3816 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3817 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3818 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3819 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3820 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3821 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3822 .features[FEAT_VMX_EXIT_CTLS] =
3823 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3824 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3825 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3826 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3827 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3828 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3829 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3830 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3831 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3832 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
3833 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3834 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3835 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3836 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3837 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3838 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3839 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3840 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3841 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3842 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3843 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3844 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3845 .features[FEAT_VMX_SECONDARY_CTLS] =
3846 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3847 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3848 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3849 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3850 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3851 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3852 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3853 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
3854 .xlevel = 0x80000008,
3855 .model_id = "Intel Core Processor (Skylake)",
3856 .versions = (X86CPUVersionDefinition[]) {
3857 { .version = 1 },
3858 {
3859 .version = 2,
3860 .alias = "Skylake-Client-IBRS",
3861 .props = (PropValue[]) {
3862 { "spec-ctrl", "on" },
3863 { "model-id",
3864 "Intel Core Processor (Skylake, IBRS)" },
3865 { /* end of list */ }
3866 }
3867 },
3868 {
3869 .version = 3,
3870 .alias = "Skylake-Client-noTSX-IBRS",
3871 .props = (PropValue[]) {
3872 { "hle", "off" },
3873 { "rtm", "off" },
3874 { "model-id",
3875 "Intel Core Processor (Skylake, IBRS, no TSX)" },
3876 { /* end of list */ }
3877 }
3878 },
3879 {
3880 .version = 4,
3881 .note = "IBRS, XSAVES, no TSX",
3882 .props = (PropValue[]) {
3883 { "xsaves", "on" },
3884 { "vmx-xsaves", "on" },
3885 { /* end of list */ }
3886 }
3887 },
3888 { /* end of list */ }
3889 }
3890 },
3891 {
3892 .name = "Skylake-Server",
3893 .level = 0xd,
3894 .vendor = CPUID_VENDOR_INTEL,
3895 .family = 6,
3896 .model = 85,
3897 .stepping = 4,
3898 .features[FEAT_1_EDX] =
3899 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3900 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3901 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3902 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3903 CPUID_DE | CPUID_FP87,
3904 .features[FEAT_1_ECX] =
3905 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3906 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3907 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3908 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3909 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3910 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3911 .features[FEAT_8000_0001_EDX] =
3912 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
3913 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3914 .features[FEAT_8000_0001_ECX] =
3915 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3916 .features[FEAT_7_0_EBX] =
3917 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
3918 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
3919 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
3920 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
3921 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLWB |
3922 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
3923 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512CD |
3924 CPUID_7_0_EBX_AVX512VL | CPUID_7_0_EBX_CLFLUSHOPT,
3925 .features[FEAT_7_0_ECX] =
3926 CPUID_7_0_ECX_PKU,
3927 /* XSAVES is added in version 5 */
3928 .features[FEAT_XSAVE] =
3929 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3930 CPUID_XSAVE_XGETBV1,
3931 .features[FEAT_6_EAX] =
3932 CPUID_6_EAX_ARAT,
3933 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
3934 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3935 MSR_VMX_BASIC_TRUE_CTLS,
3936 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3937 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3938 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3939 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3940 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3941 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3942 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3943 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3944 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3945 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3946 .features[FEAT_VMX_EXIT_CTLS] =
3947 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3948 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3949 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3950 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3951 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3952 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3953 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3954 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3955 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3956 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3957 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3958 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3959 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3960 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3961 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3962 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3963 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3964 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3965 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3966 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3967 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3968 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3969 .features[FEAT_VMX_SECONDARY_CTLS] =
3970 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3971 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3972 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3973 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3974 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3975 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3976 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3977 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3978 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3979 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3980 .xlevel = 0x80000008,
3981 .model_id = "Intel Xeon Processor (Skylake)",
3982 .versions = (X86CPUVersionDefinition[]) {
3983 { .version = 1 },
3984 {
3985 .version = 2,
3986 .alias = "Skylake-Server-IBRS",
3987 .props = (PropValue[]) {
3988 /* clflushopt was not added to Skylake-Server-IBRS */
3989 /* TODO: add -v3 including clflushopt */
3990 { "clflushopt", "off" },
3991 { "spec-ctrl", "on" },
3992 { "model-id",
3993 "Intel Xeon Processor (Skylake, IBRS)" },
3994 { /* end of list */ }
3995 }
3996 },
3997 {
3998 .version = 3,
3999 .alias = "Skylake-Server-noTSX-IBRS",
4000 .props = (PropValue[]) {
4001 { "hle", "off" },
4002 { "rtm", "off" },
4003 { "model-id",
4004 "Intel Xeon Processor (Skylake, IBRS, no TSX)" },
4005 { /* end of list */ }
4006 }
4007 },
4008 {
4009 .version = 4,
4010 .note = "IBRS, EPT switching, no TSX",
4011 .props = (PropValue[]) {
4012 { "vmx-eptp-switching", "on" },
4013 { /* end of list */ }
4014 }
4015 },
4016 {
4017 .version = 5,
4018 .note = "IBRS, XSAVES, EPT switching, no TSX",
4019 .props = (PropValue[]) {
4020 { "xsaves", "on" },
4021 { "vmx-xsaves", "on" },
4022 { /* end of list */ }
4023 }
4024 },
4025 { /* end of list */ }
4026 }
4027 },
4028 {
4029 .name = "Cascadelake-Server",
4030 .level = 0xd,
4031 .vendor = CPUID_VENDOR_INTEL,
4032 .family = 6,
4033 .model = 85,
4034 .stepping = 6,
4035 .features[FEAT_1_EDX] =
4036 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
4037 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
4038 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
4039 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
4040 CPUID_DE | CPUID_FP87,
4041 .features[FEAT_1_ECX] =
4042 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
4043 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
4044 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
4045 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
4046 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
4047 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
4048 .features[FEAT_8000_0001_EDX] =
4049 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
4050 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
4051 .features[FEAT_8000_0001_ECX] =
4052 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
4053 .features[FEAT_7_0_EBX] =
4054 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
4055 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
4056 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
4057 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
4058 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLWB |
4059 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
4060 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512CD |
4061 CPUID_7_0_EBX_AVX512VL | CPUID_7_0_EBX_CLFLUSHOPT,
4062 .features[FEAT_7_0_ECX] =
4063 CPUID_7_0_ECX_PKU |
4064 CPUID_7_0_ECX_AVX512VNNI,
4065 .features[FEAT_7_0_EDX] =
4066 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_SPEC_CTRL_SSBD,
4067 /* XSAVES is added in version 5 */
4068 .features[FEAT_XSAVE] =
4069 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
4070 CPUID_XSAVE_XGETBV1,
4071 .features[FEAT_6_EAX] =
4072 CPUID_6_EAX_ARAT,
4073 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
4074 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
4075 MSR_VMX_BASIC_TRUE_CTLS,
4076 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
4077 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
4078 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
4079 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
4080 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
4081 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
4082 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
4083 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
4084 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
4085 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
4086 .features[FEAT_VMX_EXIT_CTLS] =
4087 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
4088 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
4089 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
4090 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
4091 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
4092 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
4093 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
4094 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
4095 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
4096 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
4097 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
4098 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
4099 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
4100 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
4101 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
4102 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
4103 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
4104 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
4105 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
4106 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
4107 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
4108 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
4109 .features[FEAT_VMX_SECONDARY_CTLS] =
4110 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
4111 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
4112 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
4113 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
4114 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
4115 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
4116 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
4117 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
4118 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
4119 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
4120 .xlevel = 0x80000008,
4121 .model_id = "Intel Xeon Processor (Cascadelake)",
4122 .versions = (X86CPUVersionDefinition[]) {
4123 { .version = 1 },
4124 { .version = 2,
4125 .note = "ARCH_CAPABILITIES",
4126 .props = (PropValue[]) {
4127 { "arch-capabilities", "on" },
4128 { "rdctl-no", "on" },
4129 { "ibrs-all", "on" },
4130 { "skip-l1dfl-vmentry", "on" },
4131 { "mds-no", "on" },
4132 { /* end of list */ }
4133 },
4134 },
4135 { .version = 3,
4136 .alias = "Cascadelake-Server-noTSX",
4137 .note = "ARCH_CAPABILITIES, no TSX",
4138 .props = (PropValue[]) {
4139 { "hle", "off" },
4140 { "rtm", "off" },
4141 { /* end of list */ }
4142 },
4143 },
4144 { .version = 4,
4145 .note = "ARCH_CAPABILITIES, EPT switching, no TSX",
4146 .props = (PropValue[]) {
4147 { "vmx-eptp-switching", "on" },
4148 { /* end of list */ }
4149 },
4150 },
4151 { .version = 5,
4152 .note = "ARCH_CAPABILITIES, EPT switching, XSAVES, no TSX",
4153 .props = (PropValue[]) {
4154 { "xsaves", "on" },
4155 { "vmx-xsaves", "on" },
4156 { /* end of list */ }
4157 },
4158 },
4159 { /* end of list */ }
4160 }
4161 },
4162 {
4163 .name = "Cooperlake",
4164 .level = 0xd,
4165 .vendor = CPUID_VENDOR_INTEL,
4166 .family = 6,
4167 .model = 85,
4168 .stepping = 10,
4169 .features[FEAT_1_EDX] =
4170 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
4171 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
4172 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
4173 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
4174 CPUID_DE | CPUID_FP87,
4175 .features[FEAT_1_ECX] =
4176 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
4177 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
4178 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
4179 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
4180 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
4181 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
4182 .features[FEAT_8000_0001_EDX] =
4183 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
4184 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
4185 .features[FEAT_8000_0001_ECX] =
4186 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
4187 .features[FEAT_7_0_EBX] =
4188 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
4189 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
4190 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
4191 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
4192 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLWB |
4193 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
4194 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512CD |
4195 CPUID_7_0_EBX_AVX512VL | CPUID_7_0_EBX_CLFLUSHOPT,
4196 .features[FEAT_7_0_ECX] =
4197 CPUID_7_0_ECX_PKU |
4198 CPUID_7_0_ECX_AVX512VNNI,
4199 .features[FEAT_7_0_EDX] =
4200 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_STIBP |
4201 CPUID_7_0_EDX_SPEC_CTRL_SSBD | CPUID_7_0_EDX_ARCH_CAPABILITIES,
4202 .features[FEAT_ARCH_CAPABILITIES] =
4203 MSR_ARCH_CAP_RDCL_NO | MSR_ARCH_CAP_IBRS_ALL |
4204 MSR_ARCH_CAP_SKIP_L1DFL_VMENTRY | MSR_ARCH_CAP_MDS_NO |
4205 MSR_ARCH_CAP_PSCHANGE_MC_NO | MSR_ARCH_CAP_TAA_NO,
4206 .features[FEAT_7_1_EAX] =
4207 CPUID_7_1_EAX_AVX512_BF16,
4208 /* XSAVES is added in version 2 */
4209 .features[FEAT_XSAVE] =
4210 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
4211 CPUID_XSAVE_XGETBV1,
4212 .features[FEAT_6_EAX] =
4213 CPUID_6_EAX_ARAT,
4214 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
4215 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
4216 MSR_VMX_BASIC_TRUE_CTLS,
4217 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
4218 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
4219 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
4220 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
4221 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
4222 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
4223 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
4224 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
4225 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
4226 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
4227 .features[FEAT_VMX_EXIT_CTLS] =
4228 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
4229 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
4230 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
4231 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
4232 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
4233 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
4234 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
4235 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
4236 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
4237 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
4238 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
4239 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
4240 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
4241 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
4242 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
4243 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
4244 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
4245 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
4246 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
4247 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
4248 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
4249 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
4250 .features[FEAT_VMX_SECONDARY_CTLS] =
4251 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
4252 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
4253 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
4254 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
4255 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
4256 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
4257 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
4258 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
4259 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
4260 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
4261 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
4262 .xlevel = 0x80000008,
4263 .model_id = "Intel Xeon Processor (Cooperlake)",
4264 .versions = (X86CPUVersionDefinition[]) {
4265 { .version = 1 },
4266 { .version = 2,
4267 .note = "XSAVES",
4268 .props = (PropValue[]) {
4269 { "xsaves", "on" },
4270 { "vmx-xsaves", "on" },
4271 { /* end of list */ }
4272 },
4273 },
4274 { /* end of list */ }
4275 }
4276 },
4277 {
4278 .name = "Icelake-Server",
4279 .level = 0xd,
4280 .vendor = CPUID_VENDOR_INTEL,
4281 .family = 6,
4282 .model = 134,
4283 .stepping = 0,
4284 .features[FEAT_1_EDX] =
4285 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
4286 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
4287 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
4288 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
4289 CPUID_DE | CPUID_FP87,
4290 .features[FEAT_1_ECX] =
4291 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
4292 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
4293 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
4294 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
4295 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
4296 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
4297 .features[FEAT_8000_0001_EDX] =
4298 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
4299 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
4300 .features[FEAT_8000_0001_ECX] =
4301 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
4302 .features[FEAT_8000_0008_EBX] =
4303 CPUID_8000_0008_EBX_WBNOINVD,
4304 .features[FEAT_7_0_EBX] =
4305 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
4306 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
4307 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
4308 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
4309 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLWB |
4310 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
4311 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512CD |
4312 CPUID_7_0_EBX_AVX512VL | CPUID_7_0_EBX_CLFLUSHOPT,
4313 .features[FEAT_7_0_ECX] =
4314 CPUID_7_0_ECX_AVX512_VBMI | CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_PKU |
4315 CPUID_7_0_ECX_AVX512_VBMI2 | CPUID_7_0_ECX_GFNI |
4316 CPUID_7_0_ECX_VAES | CPUID_7_0_ECX_VPCLMULQDQ |
4317 CPUID_7_0_ECX_AVX512VNNI | CPUID_7_0_ECX_AVX512BITALG |
4318 CPUID_7_0_ECX_AVX512_VPOPCNTDQ | CPUID_7_0_ECX_LA57,
4319 .features[FEAT_7_0_EDX] =
4320 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_SPEC_CTRL_SSBD,
4321 /* XSAVES is added in version 5 */
4322 .features[FEAT_XSAVE] =
4323 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
4324 CPUID_XSAVE_XGETBV1,
4325 .features[FEAT_6_EAX] =
4326 CPUID_6_EAX_ARAT,
4327 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
4328 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
4329 MSR_VMX_BASIC_TRUE_CTLS,
4330 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
4331 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
4332 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
4333 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
4334 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
4335 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
4336 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
4337 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
4338 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
4339 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
4340 .features[FEAT_VMX_EXIT_CTLS] =
4341 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
4342 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
4343 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
4344 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
4345 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
4346 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
4347 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
4348 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
4349 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
4350 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
4351 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
4352 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
4353 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
4354 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
4355 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
4356 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
4357 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
4358 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
4359 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
4360 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
4361 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
4362 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
4363 .features[FEAT_VMX_SECONDARY_CTLS] =
4364 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
4365 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
4366 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
4367 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
4368 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
4369 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
4370 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
4371 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
4372 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS,
4373 .xlevel = 0x80000008,
4374 .model_id = "Intel Xeon Processor (Icelake)",
4375 .versions = (X86CPUVersionDefinition[]) {
4376 { .version = 1 },
4377 {
4378 .version = 2,
4379 .note = "no TSX",
4380 .alias = "Icelake-Server-noTSX",
4381 .props = (PropValue[]) {
4382 { "hle", "off" },
4383 { "rtm", "off" },
4384 { /* end of list */ }
4385 },
4386 },
4387 {
4388 .version = 3,
4389 .props = (PropValue[]) {
4390 { "arch-capabilities", "on" },
4391 { "rdctl-no", "on" },
4392 { "ibrs-all", "on" },
4393 { "skip-l1dfl-vmentry", "on" },
4394 { "mds-no", "on" },
4395 { "pschange-mc-no", "on" },
4396 { "taa-no", "on" },
4397 { /* end of list */ }
4398 },
4399 },
4400 {
4401 .version = 4,
4402 .props = (PropValue[]) {
4403 { "sha-ni", "on" },
4404 { "avx512ifma", "on" },
4405 { "rdpid", "on" },
4406 { "fsrm", "on" },
4407 { "vmx-rdseed-exit", "on" },
4408 { "vmx-pml", "on" },
4409 { "vmx-eptp-switching", "on" },
4410 { "model", "106" },
4411 { /* end of list */ }
4412 },
4413 },
4414 {
4415 .version = 5,
4416 .note = "XSAVES",
4417 .props = (PropValue[]) {
4418 { "xsaves", "on" },
4419 { "vmx-xsaves", "on" },
4420 { /* end of list */ }
4421 },
4422 },
4423 {
4424 .version = 6,
4425 .note = "5-level EPT",
4426 .props = (PropValue[]) {
4427 { "vmx-page-walk-5", "on" },
4428 { /* end of list */ }
4429 },
4430 },
4431 {
4432 .version = 7,
4433 .note = "TSX, taa-no",
4434 .props = (PropValue[]) {
4435 /* Restore TSX features removed by -v2 above */
4436 { "hle", "on" },
4437 { "rtm", "on" },
4438 { /* end of list */ }
4439 },
4440 },
4441 { /* end of list */ }
4442 }
4443 },
4444 {
4445 .name = "SapphireRapids",
4446 .level = 0x20,
4447 .vendor = CPUID_VENDOR_INTEL,
4448 .family = 6,
4449 .model = 143,
4450 .stepping = 4,
4451 /*
4452 * please keep the ascending order so that we can have a clear view of
4453 * bit position of each feature.
4454 */
4455 .features[FEAT_1_EDX] =
4456 CPUID_FP87 | CPUID_VME | CPUID_DE | CPUID_PSE | CPUID_TSC |
4457 CPUID_MSR | CPUID_PAE | CPUID_MCE | CPUID_CX8 | CPUID_APIC |
4458 CPUID_SEP | CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV |
4459 CPUID_PAT | CPUID_PSE36 | CPUID_CLFLUSH | CPUID_MMX | CPUID_FXSR |
4460 CPUID_SSE | CPUID_SSE2,
4461 .features[FEAT_1_ECX] =
4462 CPUID_EXT_SSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSSE3 |
4463 CPUID_EXT_FMA | CPUID_EXT_CX16 | CPUID_EXT_PCID | CPUID_EXT_SSE41 |
4464 CPUID_EXT_SSE42 | CPUID_EXT_X2APIC | CPUID_EXT_MOVBE |
4465 CPUID_EXT_POPCNT | CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_AES |
4466 CPUID_EXT_XSAVE | CPUID_EXT_AVX | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
4467 .features[FEAT_8000_0001_EDX] =
4468 CPUID_EXT2_SYSCALL | CPUID_EXT2_NX | CPUID_EXT2_PDPE1GB |
4469 CPUID_EXT2_RDTSCP | CPUID_EXT2_LM,
4470 .features[FEAT_8000_0001_ECX] =
4471 CPUID_EXT3_LAHF_LM | CPUID_EXT3_ABM | CPUID_EXT3_3DNOWPREFETCH,
4472 .features[FEAT_8000_0008_EBX] =
4473 CPUID_8000_0008_EBX_WBNOINVD,
4474 .features[FEAT_7_0_EBX] =
4475 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_HLE |
4476 CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 |
4477 CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID | CPUID_7_0_EBX_RTM |
4478 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
4479 CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP |
4480 CPUID_7_0_EBX_AVX512IFMA | CPUID_7_0_EBX_CLFLUSHOPT |
4481 CPUID_7_0_EBX_CLWB | CPUID_7_0_EBX_AVX512CD | CPUID_7_0_EBX_SHA_NI |
4482 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512VL,
4483 .features[FEAT_7_0_ECX] =
4484 CPUID_7_0_ECX_AVX512_VBMI | CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_PKU |
4485 CPUID_7_0_ECX_AVX512_VBMI2 | CPUID_7_0_ECX_GFNI |
4486 CPUID_7_0_ECX_VAES | CPUID_7_0_ECX_VPCLMULQDQ |
4487 CPUID_7_0_ECX_AVX512VNNI | CPUID_7_0_ECX_AVX512BITALG |
4488 CPUID_7_0_ECX_AVX512_VPOPCNTDQ | CPUID_7_0_ECX_LA57 |
4489 CPUID_7_0_ECX_RDPID | CPUID_7_0_ECX_BUS_LOCK_DETECT,
4490 .features[FEAT_7_0_EDX] =
4491 CPUID_7_0_EDX_FSRM | CPUID_7_0_EDX_SERIALIZE |
4492 CPUID_7_0_EDX_TSX_LDTRK | CPUID_7_0_EDX_AMX_BF16 |
4493 CPUID_7_0_EDX_AVX512_FP16 | CPUID_7_0_EDX_AMX_TILE |
4494 CPUID_7_0_EDX_AMX_INT8 | CPUID_7_0_EDX_SPEC_CTRL |
4495 CPUID_7_0_EDX_ARCH_CAPABILITIES | CPUID_7_0_EDX_SPEC_CTRL_SSBD,
4496 .features[FEAT_ARCH_CAPABILITIES] =
4497 MSR_ARCH_CAP_RDCL_NO | MSR_ARCH_CAP_IBRS_ALL |
4498 MSR_ARCH_CAP_SKIP_L1DFL_VMENTRY | MSR_ARCH_CAP_MDS_NO |
4499 MSR_ARCH_CAP_PSCHANGE_MC_NO | MSR_ARCH_CAP_TAA_NO,
4500 .features[FEAT_XSAVE] =
4501 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
4502 CPUID_XSAVE_XGETBV1 | CPUID_XSAVE_XSAVES | CPUID_D_1_EAX_XFD,
4503 .features[FEAT_6_EAX] =
4504 CPUID_6_EAX_ARAT,
4505 .features[FEAT_7_1_EAX] =
4506 CPUID_7_1_EAX_AVX_VNNI | CPUID_7_1_EAX_AVX512_BF16 |
4507 CPUID_7_1_EAX_FZRM | CPUID_7_1_EAX_FSRS | CPUID_7_1_EAX_FSRC,
4508 .features[FEAT_VMX_BASIC] =
4509 MSR_VMX_BASIC_INS_OUTS | MSR_VMX_BASIC_TRUE_CTLS,
4510 .features[FEAT_VMX_ENTRY_CTLS] =
4511 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_IA32E_MODE |
4512 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL |
4513 VMX_VM_ENTRY_LOAD_IA32_PAT | VMX_VM_ENTRY_LOAD_IA32_EFER,
4514 .features[FEAT_VMX_EPT_VPID_CAPS] =
4515 MSR_VMX_EPT_EXECONLY |
4516 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_PAGE_WALK_LENGTH_5 |
4517 MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB | MSR_VMX_EPT_1GB |
4518 MSR_VMX_EPT_INVEPT | MSR_VMX_EPT_AD_BITS |
4519 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
4520 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
4521 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT |
4522 MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
4523 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
4524 .features[FEAT_VMX_EXIT_CTLS] =
4525 VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
4526 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
4527 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_IA32_PAT |
4528 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
4529 VMX_VM_EXIT_LOAD_IA32_EFER | VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
4530 .features[FEAT_VMX_MISC] =
4531 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_ACTIVITY_HLT |
4532 MSR_VMX_MISC_VMWRITE_VMEXIT,
4533 .features[FEAT_VMX_PINBASED_CTLS] =
4534 VMX_PIN_BASED_EXT_INTR_MASK | VMX_PIN_BASED_NMI_EXITING |
4535 VMX_PIN_BASED_VIRTUAL_NMIS | VMX_PIN_BASED_VMX_PREEMPTION_TIMER |
4536 VMX_PIN_BASED_POSTED_INTR,
4537 .features[FEAT_VMX_PROCBASED_CTLS] =
4538 VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
4539 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
4540 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
4541 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
4542 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
4543 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
4544 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_VIRTUAL_NMI_PENDING |
4545 VMX_CPU_BASED_MOV_DR_EXITING | VMX_CPU_BASED_UNCOND_IO_EXITING |
4546 VMX_CPU_BASED_USE_IO_BITMAPS | VMX_CPU_BASED_MONITOR_TRAP_FLAG |
4547 VMX_CPU_BASED_USE_MSR_BITMAPS | VMX_CPU_BASED_MONITOR_EXITING |
4548 VMX_CPU_BASED_PAUSE_EXITING |
4549 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
4550 .features[FEAT_VMX_SECONDARY_CTLS] =
4551 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
4552 VMX_SECONDARY_EXEC_ENABLE_EPT | VMX_SECONDARY_EXEC_DESC |
4553 VMX_SECONDARY_EXEC_RDTSCP |
4554 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
4555 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_WBINVD_EXITING |
4556 VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
4557 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
4558 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
4559 VMX_SECONDARY_EXEC_RDRAND_EXITING |
4560 VMX_SECONDARY_EXEC_ENABLE_INVPCID |
4561 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
4562 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML |
4563 VMX_SECONDARY_EXEC_XSAVES,
4564 .features[FEAT_VMX_VMFUNC] =
4565 MSR_VMX_VMFUNC_EPT_SWITCHING,
4566 .xlevel = 0x80000008,
4567 .model_id = "Intel Xeon Processor (SapphireRapids)",
4568 .versions = (X86CPUVersionDefinition[]) {
4569 { .version = 1 },
4570 {
4571 .version = 2,
4572 .props = (PropValue[]) {
4573 { "sbdr-ssdp-no", "on" },
4574 { "fbsdp-no", "on" },
4575 { "psdp-no", "on" },
4576 { /* end of list */ }
4577 }
4578 },
4579 {
4580 .version = 3,
4581 .props = (PropValue[]) {
4582 { "ss", "on" },
4583 { "tsc-adjust", "on" },
4584 { "cldemote", "on" },
4585 { "movdiri", "on" },
4586 { "movdir64b", "on" },
4587 { /* end of list */ }
4588 }
4589 },
4590 { /* end of list */ }
4591 }
4592 },
4593 {
4594 .name = "GraniteRapids",
4595 .level = 0x20,
4596 .vendor = CPUID_VENDOR_INTEL,
4597 .family = 6,
4598 .model = 173,
4599 .stepping = 0,
4600 /*
4601 * please keep the ascending order so that we can have a clear view of
4602 * bit position of each feature.
4603 */
4604 .features[FEAT_1_EDX] =
4605 CPUID_FP87 | CPUID_VME | CPUID_DE | CPUID_PSE | CPUID_TSC |
4606 CPUID_MSR | CPUID_PAE | CPUID_MCE | CPUID_CX8 | CPUID_APIC |
4607 CPUID_SEP | CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV |
4608 CPUID_PAT | CPUID_PSE36 | CPUID_CLFLUSH | CPUID_MMX | CPUID_FXSR |
4609 CPUID_SSE | CPUID_SSE2,
4610 .features[FEAT_1_ECX] =
4611 CPUID_EXT_SSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSSE3 |
4612 CPUID_EXT_FMA | CPUID_EXT_CX16 | CPUID_EXT_PCID | CPUID_EXT_SSE41 |
4613 CPUID_EXT_SSE42 | CPUID_EXT_X2APIC | CPUID_EXT_MOVBE |
4614 CPUID_EXT_POPCNT | CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_AES |
4615 CPUID_EXT_XSAVE | CPUID_EXT_AVX | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
4616 .features[FEAT_8000_0001_EDX] =
4617 CPUID_EXT2_SYSCALL | CPUID_EXT2_NX | CPUID_EXT2_PDPE1GB |
4618 CPUID_EXT2_RDTSCP | CPUID_EXT2_LM,
4619 .features[FEAT_8000_0001_ECX] =
4620 CPUID_EXT3_LAHF_LM | CPUID_EXT3_ABM | CPUID_EXT3_3DNOWPREFETCH,
4621 .features[FEAT_8000_0008_EBX] =
4622 CPUID_8000_0008_EBX_WBNOINVD,
4623 .features[FEAT_7_0_EBX] =
4624 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_HLE |
4625 CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 |
4626 CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID | CPUID_7_0_EBX_RTM |
4627 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
4628 CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP |
4629 CPUID_7_0_EBX_AVX512IFMA | CPUID_7_0_EBX_CLFLUSHOPT |
4630 CPUID_7_0_EBX_CLWB | CPUID_7_0_EBX_AVX512CD | CPUID_7_0_EBX_SHA_NI |
4631 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512VL,
4632 .features[FEAT_7_0_ECX] =
4633 CPUID_7_0_ECX_AVX512_VBMI | CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_PKU |
4634 CPUID_7_0_ECX_AVX512_VBMI2 | CPUID_7_0_ECX_GFNI |
4635 CPUID_7_0_ECX_VAES | CPUID_7_0_ECX_VPCLMULQDQ |
4636 CPUID_7_0_ECX_AVX512VNNI | CPUID_7_0_ECX_AVX512BITALG |
4637 CPUID_7_0_ECX_AVX512_VPOPCNTDQ | CPUID_7_0_ECX_LA57 |
4638 CPUID_7_0_ECX_RDPID | CPUID_7_0_ECX_BUS_LOCK_DETECT,
4639 .features[FEAT_7_0_EDX] =
4640 CPUID_7_0_EDX_FSRM | CPUID_7_0_EDX_SERIALIZE |
4641 CPUID_7_0_EDX_TSX_LDTRK | CPUID_7_0_EDX_AMX_BF16 |
4642 CPUID_7_0_EDX_AVX512_FP16 | CPUID_7_0_EDX_AMX_TILE |
4643 CPUID_7_0_EDX_AMX_INT8 | CPUID_7_0_EDX_SPEC_CTRL |
4644 CPUID_7_0_EDX_ARCH_CAPABILITIES | CPUID_7_0_EDX_SPEC_CTRL_SSBD,
4645 .features[FEAT_ARCH_CAPABILITIES] =
4646 MSR_ARCH_CAP_RDCL_NO | MSR_ARCH_CAP_IBRS_ALL |
4647 MSR_ARCH_CAP_SKIP_L1DFL_VMENTRY | MSR_ARCH_CAP_MDS_NO |
4648 MSR_ARCH_CAP_PSCHANGE_MC_NO | MSR_ARCH_CAP_TAA_NO |
4649 MSR_ARCH_CAP_SBDR_SSDP_NO | MSR_ARCH_CAP_FBSDP_NO |
4650 MSR_ARCH_CAP_PSDP_NO | MSR_ARCH_CAP_PBRSB_NO,
4651 .features[FEAT_XSAVE] =
4652 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
4653 CPUID_XSAVE_XGETBV1 | CPUID_XSAVE_XSAVES | CPUID_D_1_EAX_XFD,
4654 .features[FEAT_6_EAX] =
4655 CPUID_6_EAX_ARAT,
4656 .features[FEAT_7_1_EAX] =
4657 CPUID_7_1_EAX_AVX_VNNI | CPUID_7_1_EAX_AVX512_BF16 |
4658 CPUID_7_1_EAX_FZRM | CPUID_7_1_EAX_FSRS | CPUID_7_1_EAX_FSRC |
4659 CPUID_7_1_EAX_AMX_FP16,
4660 .features[FEAT_7_1_EDX] =
4661 CPUID_7_1_EDX_PREFETCHITI,
4662 .features[FEAT_7_2_EDX] =
4663 CPUID_7_2_EDX_MCDT_NO,
4664 .features[FEAT_VMX_BASIC] =
4665 MSR_VMX_BASIC_INS_OUTS | MSR_VMX_BASIC_TRUE_CTLS,
4666 .features[FEAT_VMX_ENTRY_CTLS] =
4667 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_IA32E_MODE |
4668 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL |
4669 VMX_VM_ENTRY_LOAD_IA32_PAT | VMX_VM_ENTRY_LOAD_IA32_EFER,
4670 .features[FEAT_VMX_EPT_VPID_CAPS] =
4671 MSR_VMX_EPT_EXECONLY |
4672 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_PAGE_WALK_LENGTH_5 |
4673 MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB | MSR_VMX_EPT_1GB |
4674 MSR_VMX_EPT_INVEPT | MSR_VMX_EPT_AD_BITS |
4675 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
4676 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
4677 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT |
4678 MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
4679 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
4680 .features[FEAT_VMX_EXIT_CTLS] =
4681 VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
4682 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
4683 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_IA32_PAT |
4684 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
4685 VMX_VM_EXIT_LOAD_IA32_EFER | VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
4686 .features[FEAT_VMX_MISC] =
4687 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_ACTIVITY_HLT |
4688 MSR_VMX_MISC_VMWRITE_VMEXIT,
4689 .features[FEAT_VMX_PINBASED_CTLS] =
4690 VMX_PIN_BASED_EXT_INTR_MASK | VMX_PIN_BASED_NMI_EXITING |
4691 VMX_PIN_BASED_VIRTUAL_NMIS | VMX_PIN_BASED_VMX_PREEMPTION_TIMER |
4692 VMX_PIN_BASED_POSTED_INTR,
4693 .features[FEAT_VMX_PROCBASED_CTLS] =
4694 VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
4695 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
4696 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
4697 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
4698 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
4699 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
4700 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_VIRTUAL_NMI_PENDING |
4701 VMX_CPU_BASED_MOV_DR_EXITING | VMX_CPU_BASED_UNCOND_IO_EXITING |
4702 VMX_CPU_BASED_USE_IO_BITMAPS | VMX_CPU_BASED_MONITOR_TRAP_FLAG |
4703 VMX_CPU_BASED_USE_MSR_BITMAPS | VMX_CPU_BASED_MONITOR_EXITING |
4704 VMX_CPU_BASED_PAUSE_EXITING |
4705 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
4706 .features[FEAT_VMX_SECONDARY_CTLS] =
4707 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
4708 VMX_SECONDARY_EXEC_ENABLE_EPT | VMX_SECONDARY_EXEC_DESC |
4709 VMX_SECONDARY_EXEC_RDTSCP |
4710 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
4711 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_WBINVD_EXITING |
4712 VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
4713 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
4714 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
4715 VMX_SECONDARY_EXEC_RDRAND_EXITING |
4716 VMX_SECONDARY_EXEC_ENABLE_INVPCID |
4717 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
4718 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML |
4719 VMX_SECONDARY_EXEC_XSAVES,
4720 .features[FEAT_VMX_VMFUNC] =
4721 MSR_VMX_VMFUNC_EPT_SWITCHING,
4722 .xlevel = 0x80000008,
4723 .model_id = "Intel Xeon Processor (GraniteRapids)",
4724 .versions = (X86CPUVersionDefinition[]) {
4725 { .version = 1 },
4726 {
4727 .version = 2,
4728 .props = (PropValue[]) {
4729 { "ss", "on" },
4730 { "tsc-adjust", "on" },
4731 { "cldemote", "on" },
4732 { "movdiri", "on" },
4733 { "movdir64b", "on" },
4734 { "avx10", "on" },
4735 { "avx10-128", "on" },
4736 { "avx10-256", "on" },
4737 { "avx10-512", "on" },
4738 { "avx10-version", "1" },
4739 { "stepping", "1" },
4740 { /* end of list */ }
4741 }
4742 },
4743 { /* end of list */ },
4744 },
4745 },
4746 {
4747 .name = "SierraForest",
4748 .level = 0x23,
4749 .vendor = CPUID_VENDOR_INTEL,
4750 .family = 6,
4751 .model = 175,
4752 .stepping = 0,
4753 /*
4754 * please keep the ascending order so that we can have a clear view of
4755 * bit position of each feature.
4756 */
4757 .features[FEAT_1_EDX] =
4758 CPUID_FP87 | CPUID_VME | CPUID_DE | CPUID_PSE | CPUID_TSC |
4759 CPUID_MSR | CPUID_PAE | CPUID_MCE | CPUID_CX8 | CPUID_APIC |
4760 CPUID_SEP | CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV |
4761 CPUID_PAT | CPUID_PSE36 | CPUID_CLFLUSH | CPUID_MMX | CPUID_FXSR |
4762 CPUID_SSE | CPUID_SSE2,
4763 .features[FEAT_1_ECX] =
4764 CPUID_EXT_SSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSSE3 |
4765 CPUID_EXT_FMA | CPUID_EXT_CX16 | CPUID_EXT_PCID | CPUID_EXT_SSE41 |
4766 CPUID_EXT_SSE42 | CPUID_EXT_X2APIC | CPUID_EXT_MOVBE |
4767 CPUID_EXT_POPCNT | CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_AES |
4768 CPUID_EXT_XSAVE | CPUID_EXT_AVX | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
4769 .features[FEAT_8000_0001_EDX] =
4770 CPUID_EXT2_SYSCALL | CPUID_EXT2_NX | CPUID_EXT2_PDPE1GB |
4771 CPUID_EXT2_RDTSCP | CPUID_EXT2_LM,
4772 .features[FEAT_8000_0001_ECX] =
4773 CPUID_EXT3_LAHF_LM | CPUID_EXT3_ABM | CPUID_EXT3_3DNOWPREFETCH,
4774 .features[FEAT_8000_0008_EBX] =
4775 CPUID_8000_0008_EBX_WBNOINVD,
4776 .features[FEAT_7_0_EBX] =
4777 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
4778 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS |
4779 CPUID_7_0_EBX_INVPCID | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
4780 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT | CPUID_7_0_EBX_CLWB |
4781 CPUID_7_0_EBX_SHA_NI,
4782 .features[FEAT_7_0_ECX] =
4783 CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_PKU | CPUID_7_0_ECX_GFNI |
4784 CPUID_7_0_ECX_VAES | CPUID_7_0_ECX_VPCLMULQDQ |
4785 CPUID_7_0_ECX_RDPID | CPUID_7_0_ECX_BUS_LOCK_DETECT,
4786 .features[FEAT_7_0_EDX] =
4787 CPUID_7_0_EDX_FSRM | CPUID_7_0_EDX_SERIALIZE |
4788 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_ARCH_CAPABILITIES |
4789 CPUID_7_0_EDX_SPEC_CTRL_SSBD,
4790 .features[FEAT_ARCH_CAPABILITIES] =
4791 MSR_ARCH_CAP_RDCL_NO | MSR_ARCH_CAP_IBRS_ALL |
4792 MSR_ARCH_CAP_SKIP_L1DFL_VMENTRY | MSR_ARCH_CAP_MDS_NO |
4793 MSR_ARCH_CAP_PSCHANGE_MC_NO | MSR_ARCH_CAP_SBDR_SSDP_NO |
4794 MSR_ARCH_CAP_FBSDP_NO | MSR_ARCH_CAP_PSDP_NO |
4795 MSR_ARCH_CAP_PBRSB_NO,
4796 .features[FEAT_XSAVE] =
4797 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
4798 CPUID_XSAVE_XGETBV1 | CPUID_XSAVE_XSAVES,
4799 .features[FEAT_6_EAX] =
4800 CPUID_6_EAX_ARAT,
4801 .features[FEAT_7_1_EAX] =
4802 CPUID_7_1_EAX_AVX_VNNI | CPUID_7_1_EAX_CMPCCXADD |
4803 CPUID_7_1_EAX_FSRS | CPUID_7_1_EAX_AVX_IFMA,
4804 .features[FEAT_7_1_EDX] =
4805 CPUID_7_1_EDX_AVX_VNNI_INT8 | CPUID_7_1_EDX_AVX_NE_CONVERT,
4806 .features[FEAT_7_2_EDX] =
4807 CPUID_7_2_EDX_MCDT_NO,
4808 .features[FEAT_VMX_BASIC] =
4809 MSR_VMX_BASIC_INS_OUTS | MSR_VMX_BASIC_TRUE_CTLS,
4810 .features[FEAT_VMX_ENTRY_CTLS] =
4811 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_IA32E_MODE |
4812 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL |
4813 VMX_VM_ENTRY_LOAD_IA32_PAT | VMX_VM_ENTRY_LOAD_IA32_EFER,
4814 .features[FEAT_VMX_EPT_VPID_CAPS] =
4815 MSR_VMX_EPT_EXECONLY | MSR_VMX_EPT_PAGE_WALK_LENGTH_4 |
4816 MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB | MSR_VMX_EPT_1GB |
4817 MSR_VMX_EPT_INVEPT | MSR_VMX_EPT_AD_BITS |
4818 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
4819 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
4820 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT |
4821 MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
4822 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
4823 .features[FEAT_VMX_EXIT_CTLS] =
4824 VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
4825 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
4826 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_IA32_PAT |
4827 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
4828 VMX_VM_EXIT_LOAD_IA32_EFER | VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
4829 .features[FEAT_VMX_MISC] =
4830 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_ACTIVITY_HLT |
4831 MSR_VMX_MISC_VMWRITE_VMEXIT,
4832 .features[FEAT_VMX_PINBASED_CTLS] =
4833 VMX_PIN_BASED_EXT_INTR_MASK | VMX_PIN_BASED_NMI_EXITING |
4834 VMX_PIN_BASED_VIRTUAL_NMIS | VMX_PIN_BASED_VMX_PREEMPTION_TIMER |
4835 VMX_PIN_BASED_POSTED_INTR,
4836 .features[FEAT_VMX_PROCBASED_CTLS] =
4837 VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
4838 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
4839 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
4840 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
4841 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
4842 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
4843 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_VIRTUAL_NMI_PENDING |
4844 VMX_CPU_BASED_MOV_DR_EXITING | VMX_CPU_BASED_UNCOND_IO_EXITING |
4845 VMX_CPU_BASED_USE_IO_BITMAPS | VMX_CPU_BASED_MONITOR_TRAP_FLAG |
4846 VMX_CPU_BASED_USE_MSR_BITMAPS | VMX_CPU_BASED_MONITOR_EXITING |
4847 VMX_CPU_BASED_PAUSE_EXITING |
4848 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
4849 .features[FEAT_VMX_SECONDARY_CTLS] =
4850 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
4851 VMX_SECONDARY_EXEC_ENABLE_EPT | VMX_SECONDARY_EXEC_DESC |
4852 VMX_SECONDARY_EXEC_RDTSCP |
4853 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
4854 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_WBINVD_EXITING |
4855 VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
4856 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
4857 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
4858 VMX_SECONDARY_EXEC_RDRAND_EXITING |
4859 VMX_SECONDARY_EXEC_ENABLE_INVPCID |
4860 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
4861 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML |
4862 VMX_SECONDARY_EXEC_XSAVES,
4863 .features[FEAT_VMX_VMFUNC] =
4864 MSR_VMX_VMFUNC_EPT_SWITCHING,
4865 .xlevel = 0x80000008,
4866 .model_id = "Intel Xeon Processor (SierraForest)",
4867 .versions = (X86CPUVersionDefinition[]) {
4868 { .version = 1 },
4869 {
4870 .version = 2,
4871 .props = (PropValue[]) {
4872 { "ss", "on" },
4873 { "tsc-adjust", "on" },
4874 { "cldemote", "on" },
4875 { "movdiri", "on" },
4876 { "movdir64b", "on" },
4877 { "gds-no", "on" },
4878 { "rfds-no", "on" },
4879 { "lam", "on" },
4880 { "intel-psfd", "on"},
4881 { "ipred-ctrl", "on"},
4882 { "rrsba-ctrl", "on"},
4883 { "bhi-ctrl", "on"},
4884 { "stepping", "3" },
4885 { /* end of list */ }
4886 }
4887 },
4888 { /* end of list */ },
4889 },
4890 },
4891 {
4892 .name = "ClearwaterForest",
4893 .level = 0x23,
4894 .xlevel = 0x80000008,
4895 .vendor = CPUID_VENDOR_INTEL,
4896 .family = 6,
4897 .model = 221,
4898 .stepping = 0,
4899 /*
4900 * please keep the ascending order so that we can have a clear view of
4901 * bit position of each feature.
4902 */
4903 .features[FEAT_1_EDX] =
4904 CPUID_FP87 | CPUID_VME | CPUID_DE | CPUID_PSE | CPUID_TSC |
4905 CPUID_MSR | CPUID_PAE | CPUID_MCE | CPUID_CX8 | CPUID_APIC |
4906 CPUID_SEP | CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV |
4907 CPUID_PAT | CPUID_PSE36 | CPUID_CLFLUSH | CPUID_MMX | CPUID_FXSR |
4908 CPUID_SSE | CPUID_SSE2 | CPUID_SS,
4909 .features[FEAT_1_ECX] =
4910 CPUID_EXT_SSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSSE3 |
4911 CPUID_EXT_FMA | CPUID_EXT_CX16 | CPUID_EXT_PCID | CPUID_EXT_SSE41 |
4912 CPUID_EXT_SSE42 | CPUID_EXT_X2APIC | CPUID_EXT_MOVBE |
4913 CPUID_EXT_POPCNT | CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_AES |
4914 CPUID_EXT_XSAVE | CPUID_EXT_AVX | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
4915 .features[FEAT_8000_0001_EDX] =
4916 CPUID_EXT2_SYSCALL | CPUID_EXT2_NX | CPUID_EXT2_PDPE1GB |
4917 CPUID_EXT2_RDTSCP | CPUID_EXT2_LM,
4918 .features[FEAT_8000_0001_ECX] =
4919 CPUID_EXT3_LAHF_LM | CPUID_EXT3_ABM | CPUID_EXT3_3DNOWPREFETCH,
4920 .features[FEAT_8000_0008_EBX] =
4921 CPUID_8000_0008_EBX_WBNOINVD,
4922 .features[FEAT_7_0_EBX] =
4923 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_TSC_ADJUST |
4924 CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
4925 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
4926 CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP |
4927 CPUID_7_0_EBX_CLFLUSHOPT | CPUID_7_0_EBX_CLWB |
4928 CPUID_7_0_EBX_SHA_NI,
4929 .features[FEAT_7_0_ECX] =
4930 CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_PKU | CPUID_7_0_ECX_GFNI |
4931 CPUID_7_0_ECX_VAES | CPUID_7_0_ECX_VPCLMULQDQ |
4932 CPUID_7_0_ECX_RDPID | CPUID_7_0_ECX_BUS_LOCK_DETECT |
4933 CPUID_7_0_ECX_CLDEMOTE | CPUID_7_0_ECX_MOVDIRI |
4934 CPUID_7_0_ECX_MOVDIR64B,
4935 .features[FEAT_7_0_EDX] =
4936 CPUID_7_0_EDX_FSRM | CPUID_7_0_EDX_SERIALIZE |
4937 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_ARCH_CAPABILITIES |
4938 CPUID_7_0_EDX_SPEC_CTRL_SSBD,
4939 .features[FEAT_ARCH_CAPABILITIES] =
4940 MSR_ARCH_CAP_RDCL_NO | MSR_ARCH_CAP_IBRS_ALL |
4941 MSR_ARCH_CAP_SKIP_L1DFL_VMENTRY | MSR_ARCH_CAP_MDS_NO |
4942 MSR_ARCH_CAP_PSCHANGE_MC_NO | MSR_ARCH_CAP_SBDR_SSDP_NO |
4943 MSR_ARCH_CAP_FBSDP_NO | MSR_ARCH_CAP_PSDP_NO |
4944 MSR_ARCH_CAP_BHI_NO | MSR_ARCH_CAP_PBRSB_NO |
4945 MSR_ARCH_CAP_GDS_NO | MSR_ARCH_CAP_RFDS_NO,
4946 .features[FEAT_XSAVE] =
4947 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
4948 CPUID_XSAVE_XGETBV1 | CPUID_XSAVE_XSAVES,
4949 .features[FEAT_6_EAX] =
4950 CPUID_6_EAX_ARAT,
4951 .features[FEAT_7_1_EAX] =
4952 CPUID_7_1_EAX_SHA512 | CPUID_7_1_EAX_SM3 | CPUID_7_1_EAX_SM4 |
4953 CPUID_7_1_EAX_AVX_VNNI | CPUID_7_1_EAX_CMPCCXADD |
4954 CPUID_7_1_EAX_FSRS | CPUID_7_1_EAX_AVX_IFMA |
4955 CPUID_7_1_EAX_LAM,
4956 .features[FEAT_7_1_EDX] =
4957 CPUID_7_1_EDX_AVX_VNNI_INT8 | CPUID_7_1_EDX_AVX_NE_CONVERT |
4958 CPUID_7_1_EDX_AVX_VNNI_INT16 | CPUID_7_1_EDX_PREFETCHITI,
4959 .features[FEAT_7_2_EDX] =
4960 CPUID_7_2_EDX_PSFD | CPUID_7_2_EDX_IPRED_CTRL |
4961 CPUID_7_2_EDX_RRSBA_CTRL | CPUID_7_2_EDX_DDPD_U |
4962 CPUID_7_2_EDX_BHI_CTRL | CPUID_7_2_EDX_MCDT_NO,
4963 .features[FEAT_VMX_BASIC] =
4964 MSR_VMX_BASIC_INS_OUTS | MSR_VMX_BASIC_TRUE_CTLS,
4965 .features[FEAT_VMX_ENTRY_CTLS] =
4966 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_IA32E_MODE |
4967 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL |
4968 VMX_VM_ENTRY_LOAD_IA32_PAT | VMX_VM_ENTRY_LOAD_IA32_EFER,
4969 .features[FEAT_VMX_EPT_VPID_CAPS] =
4970 MSR_VMX_EPT_EXECONLY | MSR_VMX_EPT_PAGE_WALK_LENGTH_4 |
4971 MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB | MSR_VMX_EPT_1GB |
4972 MSR_VMX_EPT_INVEPT | MSR_VMX_EPT_AD_BITS |
4973 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
4974 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
4975 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT |
4976 MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
4977 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
4978 .features[FEAT_VMX_EXIT_CTLS] =
4979 VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
4980 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
4981 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_IA32_PAT |
4982 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
4983 VMX_VM_EXIT_LOAD_IA32_EFER | VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
4984 .features[FEAT_VMX_MISC] =
4985 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_ACTIVITY_HLT |
4986 MSR_VMX_MISC_VMWRITE_VMEXIT,
4987 .features[FEAT_VMX_PINBASED_CTLS] =
4988 VMX_PIN_BASED_EXT_INTR_MASK | VMX_PIN_BASED_NMI_EXITING |
4989 VMX_PIN_BASED_VIRTUAL_NMIS | VMX_PIN_BASED_VMX_PREEMPTION_TIMER |
4990 VMX_PIN_BASED_POSTED_INTR,
4991 .features[FEAT_VMX_PROCBASED_CTLS] =
4992 VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
4993 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
4994 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
4995 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
4996 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
4997 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
4998 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_VIRTUAL_NMI_PENDING |
4999 VMX_CPU_BASED_MOV_DR_EXITING | VMX_CPU_BASED_UNCOND_IO_EXITING |
5000 VMX_CPU_BASED_USE_IO_BITMAPS | VMX_CPU_BASED_MONITOR_TRAP_FLAG |
5001 VMX_CPU_BASED_USE_MSR_BITMAPS | VMX_CPU_BASED_MONITOR_EXITING |
5002 VMX_CPU_BASED_PAUSE_EXITING |
5003 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
5004 .features[FEAT_VMX_SECONDARY_CTLS] =
5005 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
5006 VMX_SECONDARY_EXEC_ENABLE_EPT | VMX_SECONDARY_EXEC_DESC |
5007 VMX_SECONDARY_EXEC_RDTSCP |
5008 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
5009 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_WBINVD_EXITING |
5010 VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
5011 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
5012 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
5013 VMX_SECONDARY_EXEC_RDRAND_EXITING |
5014 VMX_SECONDARY_EXEC_ENABLE_INVPCID |
5015 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
5016 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML |
5017 VMX_SECONDARY_EXEC_XSAVES,
5018 .features[FEAT_VMX_VMFUNC] =
5019 MSR_VMX_VMFUNC_EPT_SWITCHING,
5020 .model_id = "Intel Xeon Processor (ClearwaterForest)",
5021 .versions = (X86CPUVersionDefinition[]) {
5022 { .version = 1 },
5023 { /* end of list */ },
5024 },
5025 },
5026 {
5027 .name = "Denverton",
5028 .level = 21,
5029 .vendor = CPUID_VENDOR_INTEL,
5030 .family = 6,
5031 .model = 95,
5032 .stepping = 1,
5033 .features[FEAT_1_EDX] =
5034 CPUID_FP87 | CPUID_VME | CPUID_DE | CPUID_PSE | CPUID_TSC |
5035 CPUID_MSR | CPUID_PAE | CPUID_MCE | CPUID_CX8 | CPUID_APIC |
5036 CPUID_SEP | CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV |
5037 CPUID_PAT | CPUID_PSE36 | CPUID_CLFLUSH | CPUID_MMX | CPUID_FXSR |
5038 CPUID_SSE | CPUID_SSE2,
5039 .features[FEAT_1_ECX] =
5040 CPUID_EXT_SSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_MONITOR |
5041 CPUID_EXT_SSSE3 | CPUID_EXT_CX16 | CPUID_EXT_SSE41 |
5042 CPUID_EXT_SSE42 | CPUID_EXT_X2APIC | CPUID_EXT_MOVBE |
5043 CPUID_EXT_POPCNT | CPUID_EXT_TSC_DEADLINE_TIMER |
5044 CPUID_EXT_AES | CPUID_EXT_XSAVE | CPUID_EXT_RDRAND,
5045 .features[FEAT_8000_0001_EDX] =
5046 CPUID_EXT2_SYSCALL | CPUID_EXT2_NX | CPUID_EXT2_PDPE1GB |
5047 CPUID_EXT2_RDTSCP | CPUID_EXT2_LM,
5048 .features[FEAT_8000_0001_ECX] =
5049 CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
5050 .features[FEAT_7_0_EBX] =
5051 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_ERMS |
5052 CPUID_7_0_EBX_MPX | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_SMAP |
5053 CPUID_7_0_EBX_CLFLUSHOPT | CPUID_7_0_EBX_SHA_NI,
5054 .features[FEAT_7_0_EDX] =
5055 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_ARCH_CAPABILITIES |
5056 CPUID_7_0_EDX_SPEC_CTRL_SSBD,
5057 /* XSAVES is added in version 3 */
5058 .features[FEAT_XSAVE] =
5059 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC | CPUID_XSAVE_XGETBV1,
5060 .features[FEAT_6_EAX] =
5061 CPUID_6_EAX_ARAT,
5062 .features[FEAT_ARCH_CAPABILITIES] =
5063 MSR_ARCH_CAP_RDCL_NO | MSR_ARCH_CAP_SKIP_L1DFL_VMENTRY,
5064 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
5065 MSR_VMX_BASIC_TRUE_CTLS,
5066 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
5067 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
5068 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
5069 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
5070 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
5071 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
5072 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
5073 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
5074 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
5075 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
5076 .features[FEAT_VMX_EXIT_CTLS] =
5077 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
5078 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
5079 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
5080 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
5081 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
5082 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
5083 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
5084 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
5085 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
5086 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
5087 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
5088 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
5089 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
5090 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
5091 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
5092 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
5093 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
5094 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
5095 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
5096 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
5097 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
5098 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
5099 .features[FEAT_VMX_SECONDARY_CTLS] =
5100 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
5101 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
5102 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
5103 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
5104 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
5105 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
5106 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
5107 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
5108 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
5109 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
5110 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
5111 .xlevel = 0x80000008,
5112 .model_id = "Intel Atom Processor (Denverton)",
5113 .versions = (X86CPUVersionDefinition[]) {
5114 { .version = 1 },
5115 {
5116 .version = 2,
5117 .note = "no MPX, no MONITOR",
5118 .props = (PropValue[]) {
5119 { "monitor", "off" },
5120 { "mpx", "off" },
5121 { /* end of list */ },
5122 },
5123 },
5124 {
5125 .version = 3,
5126 .note = "XSAVES, no MPX, no MONITOR",
5127 .props = (PropValue[]) {
5128 { "xsaves", "on" },
5129 { "vmx-xsaves", "on" },
5130 { /* end of list */ },
5131 },
5132 },
5133 { /* end of list */ },
5134 },
5135 },
5136 {
5137 .name = "Snowridge",
5138 .level = 27,
5139 .vendor = CPUID_VENDOR_INTEL,
5140 .family = 6,
5141 .model = 134,
5142 .stepping = 1,
5143 .features[FEAT_1_EDX] =
5144 /* missing: CPUID_PN CPUID_IA64 */
5145 /* missing: CPUID_DTS, CPUID_HT, CPUID_TM, CPUID_PBE */
5146 CPUID_FP87 | CPUID_VME | CPUID_DE | CPUID_PSE |
5147 CPUID_TSC | CPUID_MSR | CPUID_PAE | CPUID_MCE |
5148 CPUID_CX8 | CPUID_APIC | CPUID_SEP |
5149 CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV |
5150 CPUID_PAT | CPUID_PSE36 | CPUID_CLFLUSH |
5151 CPUID_MMX |
5152 CPUID_FXSR | CPUID_SSE | CPUID_SSE2,
5153 .features[FEAT_1_ECX] =
5154 CPUID_EXT_SSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_MONITOR |
5155 CPUID_EXT_SSSE3 |
5156 CPUID_EXT_CX16 |
5157 CPUID_EXT_SSE41 |
5158 CPUID_EXT_SSE42 | CPUID_EXT_X2APIC | CPUID_EXT_MOVBE |
5159 CPUID_EXT_POPCNT |
5160 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_AES | CPUID_EXT_XSAVE |
5161 CPUID_EXT_RDRAND,
5162 .features[FEAT_8000_0001_EDX] =
5163 CPUID_EXT2_SYSCALL |
5164 CPUID_EXT2_NX |
5165 CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
5166 CPUID_EXT2_LM,
5167 .features[FEAT_8000_0001_ECX] =
5168 CPUID_EXT3_LAHF_LM |
5169 CPUID_EXT3_3DNOWPREFETCH,
5170 .features[FEAT_7_0_EBX] =
5171 CPUID_7_0_EBX_FSGSBASE |
5172 CPUID_7_0_EBX_SMEP |
5173 CPUID_7_0_EBX_ERMS |
5174 CPUID_7_0_EBX_MPX | /* missing bits 13, 15 */
5175 CPUID_7_0_EBX_RDSEED |
5176 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT |
5177 CPUID_7_0_EBX_CLWB |
5178 CPUID_7_0_EBX_SHA_NI,
5179 .features[FEAT_7_0_ECX] =
5180 CPUID_7_0_ECX_UMIP |
5181 /* missing bit 5 */
5182 CPUID_7_0_ECX_GFNI |
5183 CPUID_7_0_ECX_MOVDIRI | CPUID_7_0_ECX_CLDEMOTE |
5184 CPUID_7_0_ECX_MOVDIR64B,
5185 .features[FEAT_7_0_EDX] =
5186 CPUID_7_0_EDX_SPEC_CTRL |
5187 CPUID_7_0_EDX_ARCH_CAPABILITIES | CPUID_7_0_EDX_SPEC_CTRL_SSBD |
5188 CPUID_7_0_EDX_CORE_CAPABILITY,
5189 .features[FEAT_CORE_CAPABILITY] =
5190 MSR_CORE_CAP_SPLIT_LOCK_DETECT,
5191 /* XSAVES is added in version 3 */
5192 .features[FEAT_XSAVE] =
5193 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
5194 CPUID_XSAVE_XGETBV1,
5195 .features[FEAT_6_EAX] =
5196 CPUID_6_EAX_ARAT,
5197 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
5198 MSR_VMX_BASIC_TRUE_CTLS,
5199 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
5200 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
5201 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
5202 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
5203 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
5204 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
5205 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
5206 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
5207 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
5208 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
5209 .features[FEAT_VMX_EXIT_CTLS] =
5210 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
5211 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
5212 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
5213 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
5214 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
5215 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
5216 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
5217 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
5218 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
5219 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
5220 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
5221 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
5222 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
5223 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
5224 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
5225 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
5226 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
5227 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
5228 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
5229 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
5230 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
5231 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
5232 .features[FEAT_VMX_SECONDARY_CTLS] =
5233 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
5234 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
5235 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
5236 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
5237 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
5238 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
5239 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
5240 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
5241 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
5242 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
5243 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
5244 .xlevel = 0x80000008,
5245 .model_id = "Intel Atom Processor (SnowRidge)",
5246 .versions = (X86CPUVersionDefinition[]) {
5247 { .version = 1 },
5248 {
5249 .version = 2,
5250 .props = (PropValue[]) {
5251 { "mpx", "off" },
5252 { "model-id", "Intel Atom Processor (Snowridge, no MPX)" },
5253 { /* end of list */ },
5254 },
5255 },
5256 {
5257 .version = 3,
5258 .note = "XSAVES, no MPX",
5259 .props = (PropValue[]) {
5260 { "xsaves", "on" },
5261 { "vmx-xsaves", "on" },
5262 { /* end of list */ },
5263 },
5264 },
5265 {
5266 .version = 4,
5267 .note = "no split lock detect, no core-capability",
5268 .props = (PropValue[]) {
5269 { "split-lock-detect", "off" },
5270 { "core-capability", "off" },
5271 { /* end of list */ },
5272 },
5273 },
5274 { /* end of list */ },
5275 },
5276 },
5277 {
5278 .name = "KnightsMill",
5279 .level = 0xd,
5280 .vendor = CPUID_VENDOR_INTEL,
5281 .family = 6,
5282 .model = 133,
5283 .stepping = 0,
5284 .features[FEAT_1_EDX] =
5285 CPUID_VME | CPUID_SS | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR |
5286 CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV |
5287 CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC |
5288 CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC |
5289 CPUID_PSE | CPUID_DE | CPUID_FP87,
5290 .features[FEAT_1_ECX] =
5291 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
5292 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
5293 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
5294 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
5295 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
5296 CPUID_EXT_F16C | CPUID_EXT_RDRAND,
5297 .features[FEAT_8000_0001_EDX] =
5298 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
5299 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
5300 .features[FEAT_8000_0001_ECX] =
5301 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
5302 .features[FEAT_7_0_EBX] =
5303 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
5304 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS |
5305 CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_AVX512F |
5306 CPUID_7_0_EBX_AVX512CD | CPUID_7_0_EBX_AVX512PF |
5307 CPUID_7_0_EBX_AVX512ER,
5308 .features[FEAT_7_0_ECX] =
5309 CPUID_7_0_ECX_AVX512_VPOPCNTDQ,
5310 .features[FEAT_7_0_EDX] =
5311 CPUID_7_0_EDX_AVX512_4VNNIW | CPUID_7_0_EDX_AVX512_4FMAPS,
5312 .features[FEAT_XSAVE] =
5313 CPUID_XSAVE_XSAVEOPT,
5314 .features[FEAT_6_EAX] =
5315 CPUID_6_EAX_ARAT,
5316 .xlevel = 0x80000008,
5317 .model_id = "Intel Xeon Phi Processor (Knights Mill)",
5318 },
5319 {
5320 .name = "Opteron_G1",
5321 .level = 5,
5322 .vendor = CPUID_VENDOR_AMD,
5323 .family = 15,
5324 .model = 6,
5325 .stepping = 1,
5326 .features[FEAT_1_EDX] =
5327 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
5328 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
5329 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
5330 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
5331 CPUID_DE | CPUID_FP87,
5332 .features[FEAT_1_ECX] =
5333 CPUID_EXT_SSE3,
5334 .features[FEAT_8000_0001_EDX] =
5335 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
5336 .xlevel = 0x80000008,
5337 .model_id = "AMD Opteron 240 (Gen 1 Class Opteron)",
5338 },
5339 {
5340 .name = "Opteron_G2",
5341 .level = 5,
5342 .vendor = CPUID_VENDOR_AMD,
5343 .family = 15,
5344 .model = 6,
5345 .stepping = 1,
5346 .features[FEAT_1_EDX] =
5347 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
5348 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
5349 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
5350 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
5351 CPUID_DE | CPUID_FP87,
5352 .features[FEAT_1_ECX] =
5353 CPUID_EXT_CX16 | CPUID_EXT_SSE3,
5354 .features[FEAT_8000_0001_EDX] =
5355 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
5356 .features[FEAT_8000_0001_ECX] =
5357 CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM,
5358 .xlevel = 0x80000008,
5359 .model_id = "AMD Opteron 22xx (Gen 2 Class Opteron)",
5360 },
5361 {
5362 .name = "Opteron_G3",
5363 .level = 5,
5364 .vendor = CPUID_VENDOR_AMD,
5365 .family = 16,
5366 .model = 2,
5367 .stepping = 3,
5368 .features[FEAT_1_EDX] =
5369 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
5370 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
5371 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
5372 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
5373 CPUID_DE | CPUID_FP87,
5374 .features[FEAT_1_ECX] =
5375 CPUID_EXT_POPCNT | CPUID_EXT_CX16 | CPUID_EXT_MONITOR |
5376 CPUID_EXT_SSE3,
5377 .features[FEAT_8000_0001_EDX] =
5378 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL |
5379 CPUID_EXT2_RDTSCP,
5380 .features[FEAT_8000_0001_ECX] =
5381 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A |
5382 CPUID_EXT3_ABM | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM,
5383 .xlevel = 0x80000008,
5384 .model_id = "AMD Opteron 23xx (Gen 3 Class Opteron)",
5385 },
5386 {
5387 .name = "Opteron_G4",
5388 .level = 0xd,
5389 .vendor = CPUID_VENDOR_AMD,
5390 .family = 21,
5391 .model = 1,
5392 .stepping = 2,
5393 .features[FEAT_1_EDX] =
5394 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
5395 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
5396 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
5397 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
5398 CPUID_DE | CPUID_FP87,
5399 .features[FEAT_1_ECX] =
5400 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
5401 CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
5402 CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ |
5403 CPUID_EXT_SSE3,
5404 .features[FEAT_8000_0001_EDX] =
5405 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_NX |
5406 CPUID_EXT2_SYSCALL | CPUID_EXT2_RDTSCP,
5407 .features[FEAT_8000_0001_ECX] =
5408 CPUID_EXT3_FMA4 | CPUID_EXT3_XOP |
5409 CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_MISALIGNSSE |
5410 CPUID_EXT3_SSE4A | CPUID_EXT3_ABM | CPUID_EXT3_SVM |
5411 CPUID_EXT3_LAHF_LM,
5412 .features[FEAT_SVM] =
5413 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
5414 /* no xsaveopt! */
5415 .xlevel = 0x8000001A,
5416 .model_id = "AMD Opteron 62xx class CPU",
5417 },
5418 {
5419 .name = "Opteron_G5",
5420 .level = 0xd,
5421 .vendor = CPUID_VENDOR_AMD,
5422 .family = 21,
5423 .model = 2,
5424 .stepping = 0,
5425 .features[FEAT_1_EDX] =
5426 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
5427 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
5428 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
5429 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
5430 CPUID_DE | CPUID_FP87,
5431 .features[FEAT_1_ECX] =
5432 CPUID_EXT_F16C | CPUID_EXT_AVX | CPUID_EXT_XSAVE |
5433 CPUID_EXT_AES | CPUID_EXT_POPCNT | CPUID_EXT_SSE42 |
5434 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_FMA |
5435 CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3,
5436 .features[FEAT_8000_0001_EDX] =
5437 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_NX |
5438 CPUID_EXT2_SYSCALL | CPUID_EXT2_RDTSCP,
5439 .features[FEAT_8000_0001_ECX] =
5440 CPUID_EXT3_TBM | CPUID_EXT3_FMA4 | CPUID_EXT3_XOP |
5441 CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_MISALIGNSSE |
5442 CPUID_EXT3_SSE4A | CPUID_EXT3_ABM | CPUID_EXT3_SVM |
5443 CPUID_EXT3_LAHF_LM,
5444 .features[FEAT_SVM] =
5445 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
5446 /* no xsaveopt! */
5447 .xlevel = 0x8000001A,
5448 .model_id = "AMD Opteron 63xx class CPU",
5449 },
5450 {
5451 .name = "EPYC",
5452 .level = 0xd,
5453 .vendor = CPUID_VENDOR_AMD,
5454 .family = 23,
5455 .model = 1,
5456 .stepping = 2,
5457 .features[FEAT_1_EDX] =
5458 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
5459 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
5460 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
5461 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
5462 CPUID_VME | CPUID_FP87,
5463 .features[FEAT_1_ECX] =
5464 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
5465 CPUID_EXT_XSAVE | CPUID_EXT_AES | CPUID_EXT_POPCNT |
5466 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
5467 CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 |
5468 CPUID_EXT_MONITOR | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3,
5469 .features[FEAT_8000_0001_EDX] =
5470 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
5471 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
5472 CPUID_EXT2_SYSCALL,
5473 .features[FEAT_8000_0001_ECX] =
5474 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
5475 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
5476 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
5477 CPUID_EXT3_TOPOEXT,
5478 .features[FEAT_7_0_EBX] =
5479 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
5480 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_RDSEED |
5481 CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT |
5482 CPUID_7_0_EBX_SHA_NI,
5483 .features[FEAT_XSAVE] =
5484 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
5485 CPUID_XSAVE_XGETBV1,
5486 .features[FEAT_6_EAX] =
5487 CPUID_6_EAX_ARAT,
5488 .features[FEAT_SVM] =
5489 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
5490 .xlevel = 0x8000001E,
5491 .model_id = "AMD EPYC Processor",
5492 .cache_info = &epyc_cache_info,
5493 .versions = (X86CPUVersionDefinition[]) {
5494 { .version = 1 },
5495 {
5496 .version = 2,
5497 .alias = "EPYC-IBPB",
5498 .props = (PropValue[]) {
5499 { "ibpb", "on" },
5500 { "model-id",
5501 "AMD EPYC Processor (with IBPB)" },
5502 { /* end of list */ }
5503 }
5504 },
5505 {
5506 .version = 3,
5507 .props = (PropValue[]) {
5508 { "ibpb", "on" },
5509 { "perfctr-core", "on" },
5510 { "clzero", "on" },
5511 { "xsaveerptr", "on" },
5512 { "xsaves", "on" },
5513 { "model-id",
5514 "AMD EPYC Processor" },
5515 { /* end of list */ }
5516 }
5517 },
5518 {
5519 .version = 4,
5520 .props = (PropValue[]) {
5521 { "model-id",
5522 "AMD EPYC-v4 Processor" },
5523 { /* end of list */ }
5524 },
5525 .cache_info = &epyc_v4_cache_info
5526 },
5527 {
5528 .version = 5,
5529 .props = (PropValue[]) {
5530 { "overflow-recov", "on" },
5531 { "succor", "on" },
5532 { "lbrv", "on" },
5533 { "tsc-scale", "on" },
5534 { "vmcb-clean", "on" },
5535 { "flushbyasid", "on" },
5536 { "pause-filter", "on" },
5537 { "pfthreshold", "on" },
5538 { "v-vmsave-vmload", "on" },
5539 { "vgif", "on" },
5540 { "model-id",
5541 "AMD EPYC-v5 Processor" },
5542 { /* end of list */ }
5543 },
5544 .cache_info = &epyc_v5_cache_info
5545 },
5546 { /* end of list */ }
5547 }
5548 },
5549 {
5550 .name = "Dhyana",
5551 .level = 0xd,
5552 .vendor = CPUID_VENDOR_HYGON,
5553 .family = 24,
5554 .model = 0,
5555 .stepping = 1,
5556 .features[FEAT_1_EDX] =
5557 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
5558 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
5559 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
5560 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
5561 CPUID_VME | CPUID_FP87,
5562 .features[FEAT_1_ECX] =
5563 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
5564 CPUID_EXT_XSAVE | CPUID_EXT_POPCNT |
5565 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
5566 CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 |
5567 CPUID_EXT_MONITOR | CPUID_EXT_SSE3,
5568 .features[FEAT_8000_0001_EDX] =
5569 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
5570 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
5571 CPUID_EXT2_SYSCALL,
5572 .features[FEAT_8000_0001_ECX] =
5573 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
5574 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
5575 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
5576 CPUID_EXT3_TOPOEXT,
5577 .features[FEAT_8000_0008_EBX] =
5578 CPUID_8000_0008_EBX_IBPB,
5579 .features[FEAT_7_0_EBX] =
5580 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
5581 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_RDSEED |
5582 CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT,
5583 /* XSAVES is added in version 2 */
5584 .features[FEAT_XSAVE] =
5585 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
5586 CPUID_XSAVE_XGETBV1,
5587 .features[FEAT_6_EAX] =
5588 CPUID_6_EAX_ARAT,
5589 .features[FEAT_SVM] =
5590 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
5591 .xlevel = 0x8000001E,
5592 .model_id = "Hygon Dhyana Processor",
5593 .cache_info = &epyc_cache_info,
5594 .versions = (X86CPUVersionDefinition[]) {
5595 { .version = 1 },
5596 { .version = 2,
5597 .note = "XSAVES",
5598 .props = (PropValue[]) {
5599 { "xsaves", "on" },
5600 { /* end of list */ }
5601 },
5602 },
5603 { /* end of list */ }
5604 }
5605 },
5606 {
5607 .name = "EPYC-Rome",
5608 .level = 0xd,
5609 .vendor = CPUID_VENDOR_AMD,
5610 .family = 23,
5611 .model = 49,
5612 .stepping = 0,
5613 .features[FEAT_1_EDX] =
5614 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
5615 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
5616 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
5617 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
5618 CPUID_VME | CPUID_FP87,
5619 .features[FEAT_1_ECX] =
5620 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
5621 CPUID_EXT_XSAVE | CPUID_EXT_AES | CPUID_EXT_POPCNT |
5622 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
5623 CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 |
5624 CPUID_EXT_MONITOR | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3,
5625 .features[FEAT_8000_0001_EDX] =
5626 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
5627 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
5628 CPUID_EXT2_SYSCALL,
5629 .features[FEAT_8000_0001_ECX] =
5630 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
5631 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
5632 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
5633 CPUID_EXT3_TOPOEXT | CPUID_EXT3_PERFCORE,
5634 .features[FEAT_8000_0008_EBX] =
5635 CPUID_8000_0008_EBX_CLZERO | CPUID_8000_0008_EBX_XSAVEERPTR |
5636 CPUID_8000_0008_EBX_WBNOINVD | CPUID_8000_0008_EBX_IBPB |
5637 CPUID_8000_0008_EBX_STIBP,
5638 .features[FEAT_7_0_EBX] =
5639 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
5640 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_RDSEED |
5641 CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT |
5642 CPUID_7_0_EBX_SHA_NI | CPUID_7_0_EBX_CLWB,
5643 .features[FEAT_7_0_ECX] =
5644 CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_RDPID,
5645 .features[FEAT_XSAVE] =
5646 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
5647 CPUID_XSAVE_XGETBV1 | CPUID_XSAVE_XSAVES,
5648 .features[FEAT_6_EAX] =
5649 CPUID_6_EAX_ARAT,
5650 .features[FEAT_SVM] =
5651 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
5652 .xlevel = 0x8000001E,
5653 .model_id = "AMD EPYC-Rome Processor",
5654 .cache_info = &epyc_rome_cache_info,
5655 .versions = (X86CPUVersionDefinition[]) {
5656 { .version = 1 },
5657 {
5658 .version = 2,
5659 .props = (PropValue[]) {
5660 { "ibrs", "on" },
5661 { "amd-ssbd", "on" },
5662 { /* end of list */ }
5663 }
5664 },
5665 {
5666 .version = 3,
5667 .props = (PropValue[]) {
5668 { "model-id",
5669 "AMD EPYC-Rome-v3 Processor" },
5670 { /* end of list */ }
5671 },
5672 .cache_info = &epyc_rome_v3_cache_info
5673 },
5674 {
5675 .version = 4,
5676 .props = (PropValue[]) {
5677 /* Erratum 1386 */
5678 { "model-id",
5679 "AMD EPYC-Rome-v4 Processor (no XSAVES)" },
5680 { "xsaves", "off" },
5681 { /* end of list */ }
5682 },
5683 },
5684 {
5685 .version = 5,
5686 .props = (PropValue[]) {
5687 { "overflow-recov", "on" },
5688 { "succor", "on" },
5689 { "lbrv", "on" },
5690 { "tsc-scale", "on" },
5691 { "vmcb-clean", "on" },
5692 { "flushbyasid", "on" },
5693 { "pause-filter", "on" },
5694 { "pfthreshold", "on" },
5695 { "v-vmsave-vmload", "on" },
5696 { "vgif", "on" },
5697 { "model-id",
5698 "AMD EPYC-Rome-v5 Processor" },
5699 { /* end of list */ }
5700 },
5701 .cache_info = &epyc_rome_v5_cache_info
5702 },
5703 { /* end of list */ }
5704 }
5705 },
5706 {
5707 .name = "EPYC-Milan",
5708 .level = 0xd,
5709 .vendor = CPUID_VENDOR_AMD,
5710 .family = 25,
5711 .model = 1,
5712 .stepping = 1,
5713 .features[FEAT_1_EDX] =
5714 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
5715 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
5716 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
5717 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
5718 CPUID_VME | CPUID_FP87,
5719 .features[FEAT_1_ECX] =
5720 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
5721 CPUID_EXT_XSAVE | CPUID_EXT_AES | CPUID_EXT_POPCNT |
5722 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
5723 CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 |
5724 CPUID_EXT_MONITOR | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
5725 CPUID_EXT_PCID,
5726 .features[FEAT_8000_0001_EDX] =
5727 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
5728 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
5729 CPUID_EXT2_SYSCALL,
5730 .features[FEAT_8000_0001_ECX] =
5731 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
5732 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
5733 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
5734 CPUID_EXT3_TOPOEXT | CPUID_EXT3_PERFCORE,
5735 .features[FEAT_8000_0008_EBX] =
5736 CPUID_8000_0008_EBX_CLZERO | CPUID_8000_0008_EBX_XSAVEERPTR |
5737 CPUID_8000_0008_EBX_WBNOINVD | CPUID_8000_0008_EBX_IBPB |
5738 CPUID_8000_0008_EBX_IBRS | CPUID_8000_0008_EBX_STIBP |
5739 CPUID_8000_0008_EBX_AMD_SSBD,
5740 .features[FEAT_7_0_EBX] =
5741 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
5742 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_RDSEED |
5743 CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT |
5744 CPUID_7_0_EBX_SHA_NI | CPUID_7_0_EBX_CLWB | CPUID_7_0_EBX_ERMS |
5745 CPUID_7_0_EBX_INVPCID,
5746 .features[FEAT_7_0_ECX] =
5747 CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_RDPID | CPUID_7_0_ECX_PKU,
5748 .features[FEAT_7_0_EDX] =
5749 CPUID_7_0_EDX_FSRM,
5750 .features[FEAT_XSAVE] =
5751 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
5752 CPUID_XSAVE_XGETBV1 | CPUID_XSAVE_XSAVES,
5753 .features[FEAT_6_EAX] =
5754 CPUID_6_EAX_ARAT,
5755 .features[FEAT_SVM] =
5756 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE | CPUID_SVM_SVME_ADDR_CHK,
5757 .xlevel = 0x8000001E,
5758 .model_id = "AMD EPYC-Milan Processor",
5759 .cache_info = &epyc_milan_cache_info,
5760 .versions = (X86CPUVersionDefinition[]) {
5761 { .version = 1 },
5762 {
5763 .version = 2,
5764 .props = (PropValue[]) {
5765 { "model-id",
5766 "AMD EPYC-Milan-v2 Processor" },
5767 { "vaes", "on" },
5768 { "vpclmulqdq", "on" },
5769 { "stibp-always-on", "on" },
5770 { "amd-psfd", "on" },
5771 { "no-nested-data-bp", "on" },
5772 { "lfence-always-serializing", "on" },
5773 { "null-sel-clr-base", "on" },
5774 { /* end of list */ }
5775 },
5776 .cache_info = &epyc_milan_v2_cache_info
5777 },
5778 {
5779 .version = 3,
5780 .props = (PropValue[]) {
5781 { "overflow-recov", "on" },
5782 { "succor", "on" },
5783 { "lbrv", "on" },
5784 { "tsc-scale", "on" },
5785 { "vmcb-clean", "on" },
5786 { "flushbyasid", "on" },
5787 { "pause-filter", "on" },
5788 { "pfthreshold", "on" },
5789 { "v-vmsave-vmload", "on" },
5790 { "vgif", "on" },
5791 { "model-id",
5792 "AMD EPYC-Milan-v3 Processor" },
5793 { /* end of list */ }
5794 },
5795 .cache_info = &epyc_milan_v3_cache_info
5796 },
5797 { /* end of list */ }
5798 }
5799 },
5800 {
5801 .name = "EPYC-Genoa",
5802 .level = 0xd,
5803 .vendor = CPUID_VENDOR_AMD,
5804 .family = 25,
5805 .model = 17,
5806 .stepping = 0,
5807 .features[FEAT_1_EDX] =
5808 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
5809 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
5810 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
5811 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
5812 CPUID_VME | CPUID_FP87,
5813 .features[FEAT_1_ECX] =
5814 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
5815 CPUID_EXT_XSAVE | CPUID_EXT_AES | CPUID_EXT_POPCNT |
5816 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
5817 CPUID_EXT_PCID | CPUID_EXT_CX16 | CPUID_EXT_FMA |
5818 CPUID_EXT_SSSE3 | CPUID_EXT_MONITOR | CPUID_EXT_PCLMULQDQ |
5819 CPUID_EXT_SSE3,
5820 .features[FEAT_8000_0001_EDX] =
5821 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
5822 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
5823 CPUID_EXT2_SYSCALL,
5824 .features[FEAT_8000_0001_ECX] =
5825 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
5826 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
5827 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
5828 CPUID_EXT3_TOPOEXT | CPUID_EXT3_PERFCORE,
5829 .features[FEAT_8000_0008_EBX] =
5830 CPUID_8000_0008_EBX_CLZERO | CPUID_8000_0008_EBX_XSAVEERPTR |
5831 CPUID_8000_0008_EBX_WBNOINVD | CPUID_8000_0008_EBX_IBPB |
5832 CPUID_8000_0008_EBX_IBRS | CPUID_8000_0008_EBX_STIBP |
5833 CPUID_8000_0008_EBX_STIBP_ALWAYS_ON |
5834 CPUID_8000_0008_EBX_AMD_SSBD | CPUID_8000_0008_EBX_AMD_PSFD,
5835 .features[FEAT_8000_0021_EAX] =
5836 CPUID_8000_0021_EAX_NO_NESTED_DATA_BP |
5837 CPUID_8000_0021_EAX_LFENCE_ALWAYS_SERIALIZING |
5838 CPUID_8000_0021_EAX_NULL_SEL_CLR_BASE |
5839 CPUID_8000_0021_EAX_AUTO_IBRS,
5840 .features[FEAT_7_0_EBX] =
5841 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
5842 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS |
5843 CPUID_7_0_EBX_INVPCID | CPUID_7_0_EBX_AVX512F |
5844 CPUID_7_0_EBX_AVX512DQ | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
5845 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_AVX512IFMA |
5846 CPUID_7_0_EBX_CLFLUSHOPT | CPUID_7_0_EBX_CLWB |
5847 CPUID_7_0_EBX_AVX512CD | CPUID_7_0_EBX_SHA_NI |
5848 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512VL,
5849 .features[FEAT_7_0_ECX] =
5850 CPUID_7_0_ECX_AVX512_VBMI | CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_PKU |
5851 CPUID_7_0_ECX_AVX512_VBMI2 | CPUID_7_0_ECX_GFNI |
5852 CPUID_7_0_ECX_VAES | CPUID_7_0_ECX_VPCLMULQDQ |
5853 CPUID_7_0_ECX_AVX512VNNI | CPUID_7_0_ECX_AVX512BITALG |
5854 CPUID_7_0_ECX_AVX512_VPOPCNTDQ | CPUID_7_0_ECX_LA57 |
5855 CPUID_7_0_ECX_RDPID,
5856 .features[FEAT_7_0_EDX] =
5857 CPUID_7_0_EDX_FSRM,
5858 .features[FEAT_7_1_EAX] =
5859 CPUID_7_1_EAX_AVX512_BF16,
5860 .features[FEAT_XSAVE] =
5861 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
5862 CPUID_XSAVE_XGETBV1 | CPUID_XSAVE_XSAVES,
5863 .features[FEAT_6_EAX] =
5864 CPUID_6_EAX_ARAT,
5865 .features[FEAT_SVM] =
5866 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE | CPUID_SVM_VNMI |
5867 CPUID_SVM_SVME_ADDR_CHK,
5868 .xlevel = 0x80000022,
5869 .model_id = "AMD EPYC-Genoa Processor",
5870 .cache_info = &epyc_genoa_cache_info,
5871 .versions = (X86CPUVersionDefinition[]) {
5872 { .version = 1 },
5873 {
5874 .version = 2,
5875 .props = (PropValue[]) {
5876 { "overflow-recov", "on" },
5877 { "succor", "on" },
5878 { "lbrv", "on" },
5879 { "tsc-scale", "on" },
5880 { "vmcb-clean", "on" },
5881 { "flushbyasid", "on" },
5882 { "pause-filter", "on" },
5883 { "pfthreshold", "on" },
5884 { "v-vmsave-vmload", "on" },
5885 { "vgif", "on" },
5886 { "fs-gs-base-ns", "on" },
5887 { "perfmon-v2", "on" },
5888 { "model-id",
5889 "AMD EPYC-Genoa-v2 Processor" },
5890 { /* end of list */ }
5891 },
5892 .cache_info = &epyc_genoa_v2_cache_info
5893 },
5894 { /* end of list */ }
5895 }
5896 },
5897 {
5898 .name = "YongFeng",
5899 .level = 0x1F,
5900 .vendor = CPUID_VENDOR_ZHAOXIN1,
5901 .family = 7,
5902 .model = 11,
5903 .stepping = 3,
5904 /* missing: CPUID_HT, CPUID_TM, CPUID_PBE */
5905 .features[FEAT_1_EDX] =
5906 CPUID_SS | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
5907 CPUID_ACPI | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV |
5908 CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC |
5909 CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC |
5910 CPUID_PSE | CPUID_DE | CPUID_VME | CPUID_FP87,
5911 /*
5912 * missing: CPUID_EXT_OSXSAVE, CPUID_EXT_XTPR, CPUID_EXT_TM2,
5913 * CPUID_EXT_EST, CPUID_EXT_SMX, CPUID_EXT_VMX
5914 */
5915 .features[FEAT_1_ECX] =
5916 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
5917 CPUID_EXT_XSAVE | CPUID_EXT_AES | CPUID_EXT_TSC_DEADLINE_TIMER |
5918 CPUID_EXT_POPCNT | CPUID_EXT_MOVBE | CPUID_EXT_X2APIC |
5919 CPUID_EXT_SSE42 | CPUID_EXT_SSE41 | CPUID_EXT_PCID |
5920 CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 |
5921 CPUID_EXT_MONITOR | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3,
5922 .features[FEAT_7_0_EBX] =
5923 CPUID_7_0_EBX_SHA_NI | CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_ADX |
5924 CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_INVPCID | CPUID_7_0_EBX_BMI2 |
5925 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_BMI1 |
5926 CPUID_7_0_EBX_FSGSBASE,
5927 /* missing: CPUID_7_0_ECX_OSPKE */
5928 .features[FEAT_7_0_ECX] =
5929 CPUID_7_0_ECX_RDPID | CPUID_7_0_ECX_PKU | CPUID_7_0_ECX_UMIP,
5930 .features[FEAT_7_0_EDX] =
5931 CPUID_7_0_EDX_ARCH_CAPABILITIES | CPUID_7_0_EDX_SPEC_CTRL,
5932 .features[FEAT_8000_0001_EDX] =
5933 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
5934 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
5935 .features[FEAT_8000_0001_ECX] =
5936 CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM,
5937 .features[FEAT_8000_0007_EDX] = CPUID_APM_INVTSC,
5938 /*
5939 * TODO: When the Linux kernel introduces other existing definitions
5940 * for this leaf, remember to update the definitions here.
5941 */
5942 .features[FEAT_C000_0001_EDX] =
5943 CPUID_C000_0001_EDX_PMM_EN | CPUID_C000_0001_EDX_PMM |
5944 CPUID_C000_0001_EDX_PHE_EN | CPUID_C000_0001_EDX_PHE |
5945 CPUID_C000_0001_EDX_ACE2 |
5946 CPUID_C000_0001_EDX_XCRYPT_EN | CPUID_C000_0001_EDX_XCRYPT |
5947 CPUID_C000_0001_EDX_XSTORE_EN | CPUID_C000_0001_EDX_XSTORE,
5948 .features[FEAT_XSAVE] =
5949 CPUID_XSAVE_XSAVEOPT,
5950 .features[FEAT_ARCH_CAPABILITIES] =
5951 MSR_ARCH_CAP_RDCL_NO | MSR_ARCH_CAP_SKIP_L1DFL_VMENTRY |
5952 MSR_ARCH_CAP_MDS_NO | MSR_ARCH_CAP_PSCHANGE_MC_NO |
5953 MSR_ARCH_CAP_SSB_NO,
5954 .features[FEAT_VMX_PROCBASED_CTLS] =
5955 VMX_CPU_BASED_VIRTUAL_INTR_PENDING | VMX_CPU_BASED_HLT_EXITING |
5956 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_INVLPG_EXITING |
5957 VMX_CPU_BASED_MWAIT_EXITING | VMX_CPU_BASED_RDPMC_EXITING |
5958 VMX_CPU_BASED_RDTSC_EXITING | VMX_CPU_BASED_CR3_LOAD_EXITING |
5959 VMX_CPU_BASED_CR3_STORE_EXITING | VMX_CPU_BASED_CR8_LOAD_EXITING |
5960 VMX_CPU_BASED_CR8_STORE_EXITING | VMX_CPU_BASED_TPR_SHADOW |
5961 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_MOV_DR_EXITING |
5962 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
5963 VMX_CPU_BASED_MONITOR_TRAP_FLAG | VMX_CPU_BASED_USE_MSR_BITMAPS |
5964 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
5965 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
5966 /*
5967 * missing: VMX_SECONDARY_EXEC_PAUSE_LOOP_EXITING,
5968 * VMX_SECONDARY_EXEC_TSC_SCALING
5969 */
5970 .features[FEAT_VMX_SECONDARY_CTLS] =
5971 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
5972 VMX_SECONDARY_EXEC_ENABLE_EPT | VMX_SECONDARY_EXEC_DESC |
5973 VMX_SECONDARY_EXEC_RDTSCP | VMX_SECONDARY_EXEC_ENABLE_VPID |
5974 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
5975 VMX_SECONDARY_EXEC_WBINVD_EXITING |
5976 VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
5977 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
5978 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
5979 VMX_SECONDARY_EXEC_RDRAND_EXITING |
5980 VMX_SECONDARY_EXEC_ENABLE_INVPCID |
5981 VMX_SECONDARY_EXEC_ENABLE_VMFUNC |
5982 VMX_SECONDARY_EXEC_SHADOW_VMCS |
5983 VMX_SECONDARY_EXEC_ENABLE_PML,
5984 .features[FEAT_VMX_PINBASED_CTLS] =
5985 VMX_PIN_BASED_EXT_INTR_MASK | VMX_PIN_BASED_NMI_EXITING |
5986 VMX_PIN_BASED_VIRTUAL_NMIS | VMX_PIN_BASED_VMX_PREEMPTION_TIMER |
5987 VMX_PIN_BASED_POSTED_INTR,
5988 .features[FEAT_VMX_EXIT_CTLS] =
5989 VMX_VM_EXIT_SAVE_DEBUG_CONTROLS | VMX_VM_EXIT_HOST_ADDR_SPACE_SIZE |
5990 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
5991 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_IA32_PAT |
5992 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
5993 VMX_VM_EXIT_LOAD_IA32_EFER | VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
5994 /* missing: VMX_VM_ENTRY_SMM, VMX_VM_ENTRY_DEACT_DUAL_MONITOR */
5995 .features[FEAT_VMX_ENTRY_CTLS] =
5996 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_IA32E_MODE |
5997 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL |
5998 VMX_VM_ENTRY_LOAD_IA32_PAT | VMX_VM_ENTRY_LOAD_IA32_EFER,
5999 /*
6000 * missing: MSR_VMX_MISC_ACTIVITY_SHUTDOWN,
6001 * MSR_VMX_MISC_ACTIVITY_WAIT_SIPI
6002 */
6003 .features[FEAT_VMX_MISC] =
6004 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_ACTIVITY_HLT |
6005 MSR_VMX_MISC_VMWRITE_VMEXIT,
6006 /* missing: MSR_VMX_EPT_UC */
6007 .features[FEAT_VMX_EPT_VPID_CAPS] =
6008 MSR_VMX_EPT_EXECONLY | MSR_VMX_EPT_PAGE_WALK_LENGTH_4 |
6009 MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB | MSR_VMX_EPT_1GB |
6010 MSR_VMX_EPT_INVEPT | MSR_VMX_EPT_AD_BITS |
6011 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
6012 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID |
6013 MSR_VMX_EPT_INVVPID_ALL_CONTEXT | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
6014 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
6015 .features[FEAT_VMX_BASIC] =
6016 MSR_VMX_BASIC_INS_OUTS | MSR_VMX_BASIC_TRUE_CTLS,
6017 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
6018 .xlevel = 0x80000008,
6019 .model_id = "Zhaoxin YongFeng Processor",
6020 .versions = (X86CPUVersionDefinition[]) {
6021 { .version = 1 },
6022 {
6023 .version = 2,
6024 .note = "with the correct model number",
6025 .props = (PropValue[]) {
6026 { "model", "0x5b" },
6027 { /* end of list */ }
6028 }
6029 },
6030 { /* end of list */ }
6031 }
6032 },
6033 {
6034 .name = "EPYC-Turin",
6035 .level = 0xd,
6036 .vendor = CPUID_VENDOR_AMD,
6037 .family = 26,
6038 .model = 0,
6039 .stepping = 0,
6040 .features[FEAT_1_ECX] =
6041 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
6042 CPUID_EXT_XSAVE | CPUID_EXT_AES | CPUID_EXT_POPCNT |
6043 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
6044 CPUID_EXT_PCID | CPUID_EXT_CX16 | CPUID_EXT_FMA |
6045 CPUID_EXT_SSSE3 | CPUID_EXT_MONITOR | CPUID_EXT_PCLMULQDQ |
6046 CPUID_EXT_SSE3,
6047 .features[FEAT_1_EDX] =
6048 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
6049 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
6050 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
6051 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
6052 CPUID_VME | CPUID_FP87,
6053 .features[FEAT_6_EAX] =
6054 CPUID_6_EAX_ARAT,
6055 .features[FEAT_7_0_EBX] =
6056 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
6057 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS |
6058 CPUID_7_0_EBX_INVPCID | CPUID_7_0_EBX_AVX512F |
6059 CPUID_7_0_EBX_AVX512DQ | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
6060 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_AVX512IFMA |
6061 CPUID_7_0_EBX_CLFLUSHOPT | CPUID_7_0_EBX_CLWB |
6062 CPUID_7_0_EBX_AVX512CD | CPUID_7_0_EBX_SHA_NI |
6063 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512VL,
6064 .features[FEAT_7_0_ECX] =
6065 CPUID_7_0_ECX_AVX512_VBMI | CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_PKU |
6066 CPUID_7_0_ECX_AVX512_VBMI2 | CPUID_7_0_ECX_GFNI |
6067 CPUID_7_0_ECX_VAES | CPUID_7_0_ECX_VPCLMULQDQ |
6068 CPUID_7_0_ECX_AVX512VNNI | CPUID_7_0_ECX_AVX512BITALG |
6069 CPUID_7_0_ECX_AVX512_VPOPCNTDQ | CPUID_7_0_ECX_LA57 |
6070 CPUID_7_0_ECX_RDPID | CPUID_7_0_ECX_MOVDIRI |
6071 CPUID_7_0_ECX_MOVDIR64B,
6072 .features[FEAT_7_0_EDX] =
6073 CPUID_7_0_EDX_FSRM | CPUID_7_0_EDX_AVX512_VP2INTERSECT,
6074 .features[FEAT_7_1_EAX] =
6075 CPUID_7_1_EAX_AVX_VNNI | CPUID_7_1_EAX_AVX512_BF16,
6076 .features[FEAT_8000_0001_ECX] =
6077 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
6078 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
6079 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
6080 CPUID_EXT3_TOPOEXT | CPUID_EXT3_PERFCORE,
6081 .features[FEAT_8000_0001_EDX] =
6082 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
6083 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
6084 CPUID_EXT2_SYSCALL,
6085 .features[FEAT_8000_0007_EBX] =
6086 CPUID_8000_0007_EBX_OVERFLOW_RECOV | CPUID_8000_0007_EBX_SUCCOR,
6087 .features[FEAT_8000_0008_EBX] =
6088 CPUID_8000_0008_EBX_CLZERO | CPUID_8000_0008_EBX_XSAVEERPTR |
6089 CPUID_8000_0008_EBX_WBNOINVD | CPUID_8000_0008_EBX_IBPB |
6090 CPUID_8000_0008_EBX_IBRS | CPUID_8000_0008_EBX_STIBP |
6091 CPUID_8000_0008_EBX_STIBP_ALWAYS_ON |
6092 CPUID_8000_0008_EBX_AMD_SSBD | CPUID_8000_0008_EBX_AMD_PSFD,
6093 .features[FEAT_8000_0021_EAX] =
6094 CPUID_8000_0021_EAX_NO_NESTED_DATA_BP |
6095 CPUID_8000_0021_EAX_FS_GS_BASE_NS |
6096 CPUID_8000_0021_EAX_LFENCE_ALWAYS_SERIALIZING |
6097 CPUID_8000_0021_EAX_NULL_SEL_CLR_BASE |
6098 CPUID_8000_0021_EAX_AUTO_IBRS | CPUID_8000_0021_EAX_PREFETCHI |
6099 CPUID_8000_0021_EAX_SBPB | CPUID_8000_0021_EAX_IBPB_BRTYPE |
6100 CPUID_8000_0021_EAX_SRSO_USER_KERNEL_NO,
6101 .features[FEAT_8000_0022_EAX] =
6102 CPUID_8000_0022_EAX_PERFMON_V2,
6103 .features[FEAT_XSAVE] =
6104 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
6105 CPUID_XSAVE_XGETBV1 | CPUID_XSAVE_XSAVES,
6106 .features[FEAT_SVM] =
6107 CPUID_SVM_NPT | CPUID_SVM_LBRV | CPUID_SVM_NRIPSAVE |
6108 CPUID_SVM_TSCSCALE | CPUID_SVM_VMCBCLEAN | CPUID_SVM_FLUSHASID |
6109 CPUID_SVM_PAUSEFILTER | CPUID_SVM_PFTHRESHOLD |
6110 CPUID_SVM_V_VMSAVE_VMLOAD | CPUID_SVM_VGIF |
6111 CPUID_SVM_VNMI | CPUID_SVM_SVME_ADDR_CHK,
6112 .xlevel = 0x80000022,
6113 .model_id = "AMD EPYC-Turin Processor",
6114 .cache_info = &epyc_turin_cache_info,
6115 },
6116 };
6117
6118 /*
6119 * We resolve CPU model aliases using -v1 when using "-machine
6120 * none", but this is just for compatibility while libvirt isn't
6121 * adapted to resolve CPU model versions before creating VMs.
6122 * See "Runnability guarantee of CPU models" at
6123 * docs/about/deprecated.rst.
6124 */
6125 X86CPUVersion default_cpu_version = 1;
6126
x86_cpu_set_default_version(X86CPUVersion version)6127 void x86_cpu_set_default_version(X86CPUVersion version)
6128 {
6129 /* Translating CPU_VERSION_AUTO to CPU_VERSION_AUTO doesn't make sense */
6130 assert(version != CPU_VERSION_AUTO);
6131 default_cpu_version = version;
6132 }
6133
x86_cpu_model_last_version(const X86CPUModel * model)6134 static X86CPUVersion x86_cpu_model_last_version(const X86CPUModel *model)
6135 {
6136 int v = 0;
6137 const X86CPUVersionDefinition *vdef =
6138 x86_cpu_def_get_versions(model->cpudef);
6139 while (vdef->version) {
6140 v = vdef->version;
6141 vdef++;
6142 }
6143 return v;
6144 }
6145
6146 /* Return the actual version being used for a specific CPU model */
x86_cpu_model_resolve_version(const X86CPUModel * model)6147 static X86CPUVersion x86_cpu_model_resolve_version(const X86CPUModel *model)
6148 {
6149 X86CPUVersion v = model->version;
6150 if (v == CPU_VERSION_AUTO) {
6151 v = default_cpu_version;
6152 }
6153 if (v == CPU_VERSION_LATEST) {
6154 return x86_cpu_model_last_version(model);
6155 }
6156 return v;
6157 }
6158
6159 static const Property max_x86_cpu_properties[] = {
6160 DEFINE_PROP_BOOL("migratable", X86CPU, migratable, true),
6161 DEFINE_PROP_BOOL("host-cache-info", X86CPU, cache_info_passthrough, false),
6162 };
6163
max_x86_cpu_realize(DeviceState * dev,Error ** errp)6164 static void max_x86_cpu_realize(DeviceState *dev, Error **errp)
6165 {
6166 Object *obj = OBJECT(dev);
6167
6168 if (!object_property_get_int(obj, "family", &error_abort)) {
6169 if (X86_CPU(obj)->env.features[FEAT_8000_0001_EDX] & CPUID_EXT2_LM) {
6170 object_property_set_int(obj, "family", 15, &error_abort);
6171 object_property_set_int(obj, "model", 107, &error_abort);
6172 object_property_set_int(obj, "stepping", 1, &error_abort);
6173 } else {
6174 object_property_set_int(obj, "family", 6, &error_abort);
6175 object_property_set_int(obj, "model", 6, &error_abort);
6176 object_property_set_int(obj, "stepping", 3, &error_abort);
6177 }
6178 }
6179
6180 x86_cpu_realizefn(dev, errp);
6181 }
6182
max_x86_cpu_class_init(ObjectClass * oc,const void * data)6183 static void max_x86_cpu_class_init(ObjectClass *oc, const void *data)
6184 {
6185 DeviceClass *dc = DEVICE_CLASS(oc);
6186 X86CPUClass *xcc = X86_CPU_CLASS(oc);
6187
6188 xcc->ordering = 9;
6189
6190 xcc->model_description =
6191 "Enables all features supported by the accelerator in the current host";
6192
6193 device_class_set_props(dc, max_x86_cpu_properties);
6194 dc->realize = max_x86_cpu_realize;
6195 }
6196
max_x86_cpu_initfn(Object * obj)6197 static void max_x86_cpu_initfn(Object *obj)
6198 {
6199 X86CPU *cpu = X86_CPU(obj);
6200
6201 /* We can't fill the features array here because we don't know yet if
6202 * "migratable" is true or false.
6203 */
6204 cpu->max_features = true;
6205 object_property_set_bool(OBJECT(cpu), "pmu", true, &error_abort);
6206
6207 /*
6208 * these defaults are used for TCG and all other accelerators
6209 * besides KVM and HVF, which overwrite these values
6210 */
6211 object_property_set_str(OBJECT(cpu), "vendor", CPUID_VENDOR_AMD,
6212 &error_abort);
6213 object_property_set_str(OBJECT(cpu), "model-id",
6214 "QEMU TCG CPU version " QEMU_HW_VERSION,
6215 &error_abort);
6216 }
6217
6218 static const TypeInfo max_x86_cpu_type_info = {
6219 .name = X86_CPU_TYPE_NAME("max"),
6220 .parent = TYPE_X86_CPU,
6221 .instance_init = max_x86_cpu_initfn,
6222 .class_init = max_x86_cpu_class_init,
6223 };
6224
feature_word_description(FeatureWordInfo * f)6225 static char *feature_word_description(FeatureWordInfo *f)
6226 {
6227 assert(f->type == CPUID_FEATURE_WORD || f->type == MSR_FEATURE_WORD);
6228
6229 switch (f->type) {
6230 case CPUID_FEATURE_WORD:
6231 {
6232 const char *reg = get_register_name_32(f->cpuid.reg);
6233 assert(reg);
6234 if (!f->cpuid.needs_ecx) {
6235 return g_strdup_printf("CPUID[eax=%02Xh].%s", f->cpuid.eax, reg);
6236 } else {
6237 return g_strdup_printf("CPUID[eax=%02Xh,ecx=%02Xh].%s",
6238 f->cpuid.eax, f->cpuid.ecx, reg);
6239 }
6240 }
6241 case MSR_FEATURE_WORD:
6242 return g_strdup_printf("MSR(%02Xh)",
6243 f->msr.index);
6244 }
6245
6246 return NULL;
6247 }
6248
x86_cpu_have_filtered_features(X86CPU * cpu)6249 static bool x86_cpu_have_filtered_features(X86CPU *cpu)
6250 {
6251 FeatureWord w;
6252
6253 for (w = 0; w < FEATURE_WORDS; w++) {
6254 if (cpu->filtered_features[w]) {
6255 return true;
6256 }
6257 }
6258
6259 return false;
6260 }
6261
mark_unavailable_features(X86CPU * cpu,FeatureWord w,uint64_t mask,const char * verbose_prefix)6262 void mark_unavailable_features(X86CPU *cpu, FeatureWord w, uint64_t mask,
6263 const char *verbose_prefix)
6264 {
6265 CPUX86State *env = &cpu->env;
6266 FeatureWordInfo *f = &feature_word_info[w];
6267 int i;
6268 g_autofree char *feat_word_str = feature_word_description(f);
6269
6270 if (!cpu->force_features) {
6271 env->features[w] &= ~mask;
6272 }
6273 cpu->filtered_features[w] |= mask;
6274
6275 if (!verbose_prefix) {
6276 return;
6277 }
6278
6279 for (i = 0; i < 64; ++i) {
6280 if ((1ULL << i) & mask) {
6281 warn_report("%s: %s%s%s [bit %d]",
6282 verbose_prefix,
6283 feat_word_str,
6284 f->feat_names[i] ? "." : "",
6285 f->feat_names[i] ? f->feat_names[i] : "", i);
6286 }
6287 }
6288 }
6289
mark_forced_on_features(X86CPU * cpu,FeatureWord w,uint64_t mask,const char * verbose_prefix)6290 void mark_forced_on_features(X86CPU *cpu, FeatureWord w, uint64_t mask,
6291 const char *verbose_prefix)
6292 {
6293 CPUX86State *env = &cpu->env;
6294 FeatureWordInfo *f = &feature_word_info[w];
6295 int i;
6296
6297 if (!cpu->force_features) {
6298 env->features[w] |= mask;
6299 }
6300
6301 cpu->forced_on_features[w] |= mask;
6302
6303 if (!verbose_prefix) {
6304 return;
6305 }
6306
6307 for (i = 0; i < 64; ++i) {
6308 if ((1ULL << i) & mask) {
6309 g_autofree char *feat_word_str = feature_word_description(f);
6310 warn_report("%s: %s%s%s [bit %d]",
6311 verbose_prefix,
6312 feat_word_str,
6313 f->feat_names[i] ? "." : "",
6314 f->feat_names[i] ? f->feat_names[i] : "", i);
6315 }
6316 }
6317 }
6318
x86_cpuid_version_get_family(Object * obj,Visitor * v,const char * name,void * opaque,Error ** errp)6319 static void x86_cpuid_version_get_family(Object *obj, Visitor *v,
6320 const char *name, void *opaque,
6321 Error **errp)
6322 {
6323 X86CPU *cpu = X86_CPU(obj);
6324 CPUX86State *env = &cpu->env;
6325 uint64_t value;
6326
6327 value = (env->cpuid_version >> 8) & 0xf;
6328 if (value == 0xf) {
6329 value += (env->cpuid_version >> 20) & 0xff;
6330 }
6331 visit_type_uint64(v, name, &value, errp);
6332 }
6333
x86_cpuid_version_set_family(Object * obj,Visitor * v,const char * name,void * opaque,Error ** errp)6334 static void x86_cpuid_version_set_family(Object *obj, Visitor *v,
6335 const char *name, void *opaque,
6336 Error **errp)
6337 {
6338 X86CPU *cpu = X86_CPU(obj);
6339 CPUX86State *env = &cpu->env;
6340 const uint64_t max = 0xff + 0xf;
6341 uint64_t value;
6342
6343 if (!visit_type_uint64(v, name, &value, errp)) {
6344 return;
6345 }
6346 if (value > max) {
6347 error_setg(errp, "parameter '%s' can be at most %" PRIu64,
6348 name ? name : "null", max);
6349 return;
6350 }
6351
6352 env->cpuid_version &= ~0xff00f00;
6353 if (value > 0x0f) {
6354 env->cpuid_version |= 0xf00 | ((value - 0x0f) << 20);
6355 } else {
6356 env->cpuid_version |= value << 8;
6357 }
6358 }
6359
x86_cpuid_version_get_model(Object * obj,Visitor * v,const char * name,void * opaque,Error ** errp)6360 static void x86_cpuid_version_get_model(Object *obj, Visitor *v,
6361 const char *name, void *opaque,
6362 Error **errp)
6363 {
6364 X86CPU *cpu = X86_CPU(obj);
6365 CPUX86State *env = &cpu->env;
6366 uint64_t value;
6367
6368 value = (env->cpuid_version >> 4) & 0xf;
6369 value |= ((env->cpuid_version >> 16) & 0xf) << 4;
6370 visit_type_uint64(v, name, &value, errp);
6371 }
6372
x86_cpuid_version_set_model(Object * obj,Visitor * v,const char * name,void * opaque,Error ** errp)6373 static void x86_cpuid_version_set_model(Object *obj, Visitor *v,
6374 const char *name, void *opaque,
6375 Error **errp)
6376 {
6377 X86CPU *cpu = X86_CPU(obj);
6378 CPUX86State *env = &cpu->env;
6379 const uint64_t max = 0xff;
6380 uint64_t value;
6381
6382 if (!visit_type_uint64(v, name, &value, errp)) {
6383 return;
6384 }
6385 if (value > max) {
6386 error_setg(errp, "parameter '%s' can be at most %" PRIu64,
6387 name ? name : "null", max);
6388 return;
6389 }
6390
6391 env->cpuid_version &= ~0xf00f0;
6392 env->cpuid_version |= ((value & 0xf) << 4) | ((value >> 4) << 16);
6393 }
6394
x86_cpuid_version_get_stepping(Object * obj,Visitor * v,const char * name,void * opaque,Error ** errp)6395 static void x86_cpuid_version_get_stepping(Object *obj, Visitor *v,
6396 const char *name, void *opaque,
6397 Error **errp)
6398 {
6399 X86CPU *cpu = X86_CPU(obj);
6400 CPUX86State *env = &cpu->env;
6401 uint64_t value;
6402
6403 value = env->cpuid_version & 0xf;
6404 visit_type_uint64(v, name, &value, errp);
6405 }
6406
x86_cpuid_version_set_stepping(Object * obj,Visitor * v,const char * name,void * opaque,Error ** errp)6407 static void x86_cpuid_version_set_stepping(Object *obj, Visitor *v,
6408 const char *name, void *opaque,
6409 Error **errp)
6410 {
6411 X86CPU *cpu = X86_CPU(obj);
6412 CPUX86State *env = &cpu->env;
6413 const uint64_t max = 0xf;
6414 uint64_t value;
6415
6416 if (!visit_type_uint64(v, name, &value, errp)) {
6417 return;
6418 }
6419 if (value > max) {
6420 error_setg(errp, "parameter '%s' can be at most %" PRIu64,
6421 name ? name : "null", max);
6422 return;
6423 }
6424
6425 env->cpuid_version &= ~0xf;
6426 env->cpuid_version |= value & 0xf;
6427 }
6428
x86_cpuid_get_vendor(Object * obj,Error ** errp)6429 static char *x86_cpuid_get_vendor(Object *obj, Error **errp)
6430 {
6431 X86CPU *cpu = X86_CPU(obj);
6432 CPUX86State *env = &cpu->env;
6433 char *value;
6434
6435 value = g_malloc(CPUID_VENDOR_SZ + 1);
6436 x86_cpu_vendor_words2str(value, env->cpuid_vendor1, env->cpuid_vendor2,
6437 env->cpuid_vendor3);
6438 return value;
6439 }
6440
x86_cpuid_set_vendor(Object * obj,const char * value,Error ** errp)6441 static void x86_cpuid_set_vendor(Object *obj, const char *value,
6442 Error **errp)
6443 {
6444 X86CPU *cpu = X86_CPU(obj);
6445 CPUX86State *env = &cpu->env;
6446 int i;
6447
6448 if (strlen(value) != CPUID_VENDOR_SZ) {
6449 error_setg(errp, "value of property 'vendor' must consist of"
6450 " exactly " stringify(CPUID_VENDOR_SZ) " characters");
6451 return;
6452 }
6453
6454 env->cpuid_vendor1 = 0;
6455 env->cpuid_vendor2 = 0;
6456 env->cpuid_vendor3 = 0;
6457 for (i = 0; i < 4; i++) {
6458 env->cpuid_vendor1 |= ((uint8_t)value[i ]) << (8 * i);
6459 env->cpuid_vendor2 |= ((uint8_t)value[i + 4]) << (8 * i);
6460 env->cpuid_vendor3 |= ((uint8_t)value[i + 8]) << (8 * i);
6461 }
6462 }
6463
x86_cpuid_get_model_id(Object * obj,Error ** errp)6464 static char *x86_cpuid_get_model_id(Object *obj, Error **errp)
6465 {
6466 X86CPU *cpu = X86_CPU(obj);
6467 CPUX86State *env = &cpu->env;
6468 char *value;
6469 int i;
6470
6471 value = g_malloc(48 + 1);
6472 for (i = 0; i < 48; i++) {
6473 value[i] = env->cpuid_model[i >> 2] >> (8 * (i & 3));
6474 }
6475 value[48] = '\0';
6476 return value;
6477 }
6478
x86_cpuid_set_model_id(Object * obj,const char * model_id,Error ** errp)6479 static void x86_cpuid_set_model_id(Object *obj, const char *model_id,
6480 Error **errp)
6481 {
6482 X86CPU *cpu = X86_CPU(obj);
6483 CPUX86State *env = &cpu->env;
6484 int c, len, i;
6485
6486 if (model_id == NULL) {
6487 model_id = "";
6488 }
6489 len = strlen(model_id);
6490 memset(env->cpuid_model, 0, 48);
6491 for (i = 0; i < 48; i++) {
6492 if (i >= len) {
6493 c = '\0';
6494 } else {
6495 c = (uint8_t)model_id[i];
6496 }
6497 env->cpuid_model[i >> 2] |= c << (8 * (i & 3));
6498 }
6499 }
6500
x86_cpuid_get_tsc_freq(Object * obj,Visitor * v,const char * name,void * opaque,Error ** errp)6501 static void x86_cpuid_get_tsc_freq(Object *obj, Visitor *v, const char *name,
6502 void *opaque, Error **errp)
6503 {
6504 X86CPU *cpu = X86_CPU(obj);
6505 int64_t value;
6506
6507 value = cpu->env.tsc_khz * 1000;
6508 visit_type_int(v, name, &value, errp);
6509 }
6510
x86_cpuid_set_tsc_freq(Object * obj,Visitor * v,const char * name,void * opaque,Error ** errp)6511 static void x86_cpuid_set_tsc_freq(Object *obj, Visitor *v, const char *name,
6512 void *opaque, Error **errp)
6513 {
6514 X86CPU *cpu = X86_CPU(obj);
6515 const int64_t max = INT64_MAX;
6516 int64_t value;
6517
6518 if (!visit_type_int(v, name, &value, errp)) {
6519 return;
6520 }
6521 if (value < 0 || value > max) {
6522 error_setg(errp, "parameter '%s' can be at most %" PRId64,
6523 name ? name : "null", max);
6524 return;
6525 }
6526
6527 cpu->env.tsc_khz = cpu->env.user_tsc_khz = value / 1000;
6528 }
6529
6530 /* Generic getter for "feature-words" and "filtered-features" properties */
x86_cpu_get_feature_words(Object * obj,Visitor * v,const char * name,void * opaque,Error ** errp)6531 static void x86_cpu_get_feature_words(Object *obj, Visitor *v,
6532 const char *name, void *opaque,
6533 Error **errp)
6534 {
6535 uint64_t *array = (uint64_t *)opaque;
6536 FeatureWord w;
6537 X86CPUFeatureWordInfo word_infos[FEATURE_WORDS] = { };
6538 X86CPUFeatureWordInfoList list_entries[FEATURE_WORDS] = { };
6539 X86CPUFeatureWordInfoList *list = NULL;
6540
6541 for (w = 0; w < FEATURE_WORDS; w++) {
6542 FeatureWordInfo *wi = &feature_word_info[w];
6543 /*
6544 * We didn't have MSR features when "feature-words" was
6545 * introduced. Therefore skipped other type entries.
6546 */
6547 if (wi->type != CPUID_FEATURE_WORD) {
6548 continue;
6549 }
6550 X86CPUFeatureWordInfo *qwi = &word_infos[w];
6551 qwi->cpuid_input_eax = wi->cpuid.eax;
6552 qwi->has_cpuid_input_ecx = wi->cpuid.needs_ecx;
6553 qwi->cpuid_input_ecx = wi->cpuid.ecx;
6554 qwi->cpuid_register = x86_reg_info_32[wi->cpuid.reg].qapi_enum;
6555 qwi->features = array[w];
6556
6557 /* List will be in reverse order, but order shouldn't matter */
6558 list_entries[w].next = list;
6559 list_entries[w].value = &word_infos[w];
6560 list = &list_entries[w];
6561 }
6562
6563 visit_type_X86CPUFeatureWordInfoList(v, "feature-words", &list, errp);
6564 }
6565
6566 /* Convert all '_' in a feature string option name to '-', to make feature
6567 * name conform to QOM property naming rule, which uses '-' instead of '_'.
6568 */
feat2prop(char * s)6569 static inline void feat2prop(char *s)
6570 {
6571 while ((s = strchr(s, '_'))) {
6572 *s = '-';
6573 }
6574 }
6575
6576 /* Return the feature property name for a feature flag bit */
x86_cpu_feature_name(FeatureWord w,int bitnr)6577 static const char *x86_cpu_feature_name(FeatureWord w, int bitnr)
6578 {
6579 const char *name;
6580 /* XSAVE components are automatically enabled by other features,
6581 * so return the original feature name instead
6582 */
6583 if (w == FEAT_XSAVE_XCR0_LO || w == FEAT_XSAVE_XCR0_HI) {
6584 int comp = (w == FEAT_XSAVE_XCR0_HI) ? bitnr + 32 : bitnr;
6585
6586 if (comp < ARRAY_SIZE(x86_ext_save_areas) &&
6587 x86_ext_save_areas[comp].bits) {
6588 w = x86_ext_save_areas[comp].feature;
6589 bitnr = ctz32(x86_ext_save_areas[comp].bits);
6590 }
6591 }
6592
6593 assert(bitnr < 64);
6594 assert(w < FEATURE_WORDS);
6595 name = feature_word_info[w].feat_names[bitnr];
6596 assert(bitnr < 32 || !(name && feature_word_info[w].type == CPUID_FEATURE_WORD));
6597 return name;
6598 }
6599
6600 /* Compatibility hack to maintain legacy +-feat semantic,
6601 * where +-feat overwrites any feature set by
6602 * feat=on|feat even if the later is parsed after +-feat
6603 * (i.e. "-x2apic,x2apic=on" will result in x2apic disabled)
6604 */
6605 static GList *plus_features, *minus_features;
6606
compare_string(gconstpointer a,gconstpointer b)6607 static gint compare_string(gconstpointer a, gconstpointer b)
6608 {
6609 return g_strcmp0(a, b);
6610 }
6611
6612 /* Parse "+feature,-feature,feature=foo" CPU feature string
6613 */
x86_cpu_parse_featurestr(const char * typename,char * features,Error ** errp)6614 static void x86_cpu_parse_featurestr(const char *typename, char *features,
6615 Error **errp)
6616 {
6617 char *featurestr; /* Single 'key=value" string being parsed */
6618 static bool cpu_globals_initialized;
6619 bool ambiguous = false;
6620
6621 if (cpu_globals_initialized) {
6622 return;
6623 }
6624 cpu_globals_initialized = true;
6625
6626 if (!features) {
6627 return;
6628 }
6629
6630 for (featurestr = strtok(features, ",");
6631 featurestr;
6632 featurestr = strtok(NULL, ",")) {
6633 const char *name;
6634 const char *val = NULL;
6635 char *eq = NULL;
6636 char num[32];
6637 GlobalProperty *prop;
6638
6639 /* Compatibility syntax: */
6640 if (featurestr[0] == '+') {
6641 plus_features = g_list_append(plus_features,
6642 g_strdup(featurestr + 1));
6643 continue;
6644 } else if (featurestr[0] == '-') {
6645 minus_features = g_list_append(minus_features,
6646 g_strdup(featurestr + 1));
6647 continue;
6648 }
6649
6650 eq = strchr(featurestr, '=');
6651 if (eq) {
6652 *eq++ = 0;
6653 val = eq;
6654 } else {
6655 val = "on";
6656 }
6657
6658 feat2prop(featurestr);
6659 name = featurestr;
6660
6661 if (g_list_find_custom(plus_features, name, compare_string)) {
6662 warn_report("Ambiguous CPU model string. "
6663 "Don't mix both \"+%s\" and \"%s=%s\"",
6664 name, name, val);
6665 ambiguous = true;
6666 }
6667 if (g_list_find_custom(minus_features, name, compare_string)) {
6668 warn_report("Ambiguous CPU model string. "
6669 "Don't mix both \"-%s\" and \"%s=%s\"",
6670 name, name, val);
6671 ambiguous = true;
6672 }
6673
6674 /* Special case: */
6675 if (!strcmp(name, "tsc-freq")) {
6676 int ret;
6677 uint64_t tsc_freq;
6678
6679 ret = qemu_strtosz_metric(val, NULL, &tsc_freq);
6680 if (ret < 0 || tsc_freq > INT64_MAX) {
6681 error_setg(errp, "bad numerical value %s", val);
6682 return;
6683 }
6684 snprintf(num, sizeof(num), "%" PRId64, tsc_freq);
6685 val = num;
6686 name = "tsc-frequency";
6687 }
6688
6689 prop = g_new0(typeof(*prop), 1);
6690 prop->driver = typename;
6691 prop->property = g_strdup(name);
6692 prop->value = g_strdup(val);
6693 qdev_prop_register_global(prop);
6694 }
6695
6696 if (ambiguous) {
6697 warn_report("Compatibility of ambiguous CPU model "
6698 "strings won't be kept on future QEMU versions");
6699 }
6700 }
6701
6702 static bool x86_cpu_filter_features(X86CPU *cpu, bool verbose);
6703
6704 /* Build a list with the name of all features on a feature word array */
x86_cpu_list_feature_names(FeatureWordArray features,strList ** list)6705 static void x86_cpu_list_feature_names(FeatureWordArray features,
6706 strList **list)
6707 {
6708 strList **tail = list;
6709 FeatureWord w;
6710
6711 for (w = 0; w < FEATURE_WORDS; w++) {
6712 uint64_t filtered = features[w];
6713 int i;
6714 for (i = 0; i < 64; i++) {
6715 if (filtered & (1ULL << i)) {
6716 QAPI_LIST_APPEND(tail, g_strdup(x86_cpu_feature_name(w, i)));
6717 }
6718 }
6719 }
6720 }
6721
x86_cpu_get_unavailable_features(Object * obj,Visitor * v,const char * name,void * opaque,Error ** errp)6722 static void x86_cpu_get_unavailable_features(Object *obj, Visitor *v,
6723 const char *name, void *opaque,
6724 Error **errp)
6725 {
6726 X86CPU *xc = X86_CPU(obj);
6727 strList *result = NULL;
6728
6729 x86_cpu_list_feature_names(xc->filtered_features, &result);
6730 visit_type_strList(v, "unavailable-features", &result, errp);
6731 }
6732
6733 /* Print all cpuid feature names in featureset
6734 */
listflags(GList * features)6735 static void listflags(GList *features)
6736 {
6737 size_t len = 0;
6738 GList *tmp;
6739
6740 for (tmp = features; tmp; tmp = tmp->next) {
6741 const char *name = tmp->data;
6742 if ((len + strlen(name) + 1) >= 75) {
6743 qemu_printf("\n");
6744 len = 0;
6745 }
6746 qemu_printf("%s%s", len == 0 ? " " : " ", name);
6747 len += strlen(name) + 1;
6748 }
6749 qemu_printf("\n");
6750 }
6751
6752 /* Sort alphabetically by type name, respecting X86CPUClass::ordering. */
x86_cpu_list_compare(gconstpointer a,gconstpointer b,gpointer d)6753 static gint x86_cpu_list_compare(gconstpointer a, gconstpointer b, gpointer d)
6754 {
6755 ObjectClass *class_a = (ObjectClass *)a;
6756 ObjectClass *class_b = (ObjectClass *)b;
6757 X86CPUClass *cc_a = X86_CPU_CLASS(class_a);
6758 X86CPUClass *cc_b = X86_CPU_CLASS(class_b);
6759 int ret;
6760
6761 if (cc_a->ordering != cc_b->ordering) {
6762 ret = cc_a->ordering - cc_b->ordering;
6763 } else {
6764 g_autofree char *name_a = x86_cpu_class_get_model_name(cc_a);
6765 g_autofree char *name_b = x86_cpu_class_get_model_name(cc_b);
6766 ret = strcmp(name_a, name_b);
6767 }
6768 return ret;
6769 }
6770
get_sorted_cpu_model_list(void)6771 static GSList *get_sorted_cpu_model_list(void)
6772 {
6773 GSList *list = object_class_get_list(TYPE_X86_CPU, false);
6774 list = g_slist_sort_with_data(list, x86_cpu_list_compare, NULL);
6775 return list;
6776 }
6777
x86_cpu_class_get_model_id(X86CPUClass * xc)6778 static char *x86_cpu_class_get_model_id(X86CPUClass *xc)
6779 {
6780 Object *obj = object_new_with_class(OBJECT_CLASS(xc));
6781 char *r = object_property_get_str(obj, "model-id", &error_abort);
6782 object_unref(obj);
6783 return r;
6784 }
6785
x86_cpu_class_get_alias_of(X86CPUClass * cc)6786 static char *x86_cpu_class_get_alias_of(X86CPUClass *cc)
6787 {
6788 X86CPUVersion version;
6789
6790 if (!cc->model || !cc->model->is_alias) {
6791 return NULL;
6792 }
6793 version = x86_cpu_model_resolve_version(cc->model);
6794 if (version <= 0) {
6795 return NULL;
6796 }
6797 return x86_cpu_versioned_model_name(cc->model->cpudef, version);
6798 }
6799
x86_cpu_list_entry(gpointer data,gpointer user_data)6800 static void x86_cpu_list_entry(gpointer data, gpointer user_data)
6801 {
6802 ObjectClass *oc = data;
6803 X86CPUClass *cc = X86_CPU_CLASS(oc);
6804 g_autofree char *name = x86_cpu_class_get_model_name(cc);
6805 g_autofree char *desc = g_strdup(cc->model_description);
6806 g_autofree char *alias_of = x86_cpu_class_get_alias_of(cc);
6807 g_autofree char *model_id = x86_cpu_class_get_model_id(cc);
6808
6809 if (!desc && alias_of) {
6810 if (cc->model && cc->model->version == CPU_VERSION_AUTO) {
6811 desc = g_strdup("(alias configured by machine type)");
6812 } else {
6813 desc = g_strdup_printf("(alias of %s)", alias_of);
6814 }
6815 }
6816 if (!desc && cc->model && cc->model->note) {
6817 desc = g_strdup_printf("%s [%s]", model_id, cc->model->note);
6818 }
6819 if (!desc) {
6820 desc = g_strdup(model_id);
6821 }
6822
6823 if (cc->model && cc->model->cpudef->deprecation_note) {
6824 g_autofree char *olddesc = desc;
6825 desc = g_strdup_printf("%s (deprecated)", olddesc);
6826 }
6827
6828 qemu_printf(" %-20s %s\n", name, desc);
6829 }
6830
strcmp_wrap(gconstpointer a,gconstpointer b,gpointer d)6831 static gint strcmp_wrap(gconstpointer a, gconstpointer b, gpointer d)
6832 {
6833 return strcmp(a, b);
6834 }
6835
6836 /* list available CPU models and flags */
x86_cpu_list(void)6837 static void x86_cpu_list(void)
6838 {
6839 int i, j;
6840 GSList *list;
6841 GList *names = NULL;
6842
6843 qemu_printf("Available CPUs:\n");
6844 list = get_sorted_cpu_model_list();
6845 g_slist_foreach(list, x86_cpu_list_entry, NULL);
6846 g_slist_free(list);
6847
6848 names = NULL;
6849 for (i = 0; i < ARRAY_SIZE(feature_word_info); i++) {
6850 FeatureWordInfo *fw = &feature_word_info[i];
6851 for (j = 0; j < 64; j++) {
6852 if (fw->feat_names[j]) {
6853 names = g_list_append(names, (gpointer)fw->feat_names[j]);
6854 }
6855 }
6856 }
6857
6858 names = g_list_sort_with_data(names, strcmp_wrap, NULL);
6859
6860 qemu_printf("\nRecognized CPUID flags:\n");
6861 listflags(names);
6862 qemu_printf("\n");
6863 g_list_free(names);
6864 }
6865
6866 #ifndef CONFIG_USER_ONLY
6867
6868 /* Check for missing features that may prevent the CPU class from
6869 * running using the current machine and accelerator.
6870 */
x86_cpu_class_check_missing_features(X86CPUClass * xcc,strList ** list)6871 static void x86_cpu_class_check_missing_features(X86CPUClass *xcc,
6872 strList **list)
6873 {
6874 strList **tail = list;
6875 X86CPU *xc;
6876 Error *err = NULL;
6877
6878 if (xcc->host_cpuid_required && !accel_uses_host_cpuid()) {
6879 QAPI_LIST_APPEND(tail, g_strdup("kvm"));
6880 return;
6881 }
6882
6883 xc = X86_CPU(object_new_with_class(OBJECT_CLASS(xcc)));
6884
6885 x86_cpu_expand_features(xc, &err);
6886 if (err) {
6887 /* Errors at x86_cpu_expand_features should never happen,
6888 * but in case it does, just report the model as not
6889 * runnable at all using the "type" property.
6890 */
6891 QAPI_LIST_APPEND(tail, g_strdup("type"));
6892 error_free(err);
6893 }
6894
6895 x86_cpu_filter_features(xc, false);
6896
6897 x86_cpu_list_feature_names(xc->filtered_features, tail);
6898
6899 object_unref(OBJECT(xc));
6900 }
6901
x86_cpu_definition_entry(gpointer data,gpointer user_data)6902 static void x86_cpu_definition_entry(gpointer data, gpointer user_data)
6903 {
6904 ObjectClass *oc = data;
6905 X86CPUClass *cc = X86_CPU_CLASS(oc);
6906 CpuDefinitionInfoList **cpu_list = user_data;
6907 CpuDefinitionInfo *info;
6908
6909 info = g_malloc0(sizeof(*info));
6910 info->name = x86_cpu_class_get_model_name(cc);
6911 x86_cpu_class_check_missing_features(cc, &info->unavailable_features);
6912 info->has_unavailable_features = true;
6913 info->q_typename = g_strdup(object_class_get_name(oc));
6914 info->migration_safe = cc->migration_safe;
6915 info->has_migration_safe = true;
6916 info->q_static = cc->static_model;
6917 if (cc->model && cc->model->cpudef->deprecation_note) {
6918 info->deprecated = true;
6919 } else {
6920 info->deprecated = false;
6921 }
6922 /*
6923 * Old machine types won't report aliases, so that alias translation
6924 * doesn't break compatibility with previous QEMU versions.
6925 */
6926 if (default_cpu_version != CPU_VERSION_LEGACY) {
6927 info->alias_of = x86_cpu_class_get_alias_of(cc);
6928 }
6929
6930 QAPI_LIST_PREPEND(*cpu_list, info);
6931 }
6932
qmp_query_cpu_definitions(Error ** errp)6933 CpuDefinitionInfoList *qmp_query_cpu_definitions(Error **errp)
6934 {
6935 CpuDefinitionInfoList *cpu_list = NULL;
6936 GSList *list = get_sorted_cpu_model_list();
6937 g_slist_foreach(list, x86_cpu_definition_entry, &cpu_list);
6938 g_slist_free(list);
6939 return cpu_list;
6940 }
6941
6942 #endif /* !CONFIG_USER_ONLY */
6943
x86_cpu_get_supported_feature_word(X86CPU * cpu,FeatureWord w)6944 uint64_t x86_cpu_get_supported_feature_word(X86CPU *cpu, FeatureWord w)
6945 {
6946 FeatureWordInfo *wi = &feature_word_info[w];
6947 uint64_t r = 0;
6948 uint64_t unavail = 0;
6949
6950 if (kvm_enabled()) {
6951 switch (wi->type) {
6952 case CPUID_FEATURE_WORD:
6953 r = kvm_arch_get_supported_cpuid(kvm_state, wi->cpuid.eax,
6954 wi->cpuid.ecx,
6955 wi->cpuid.reg);
6956 break;
6957 case MSR_FEATURE_WORD:
6958 r = kvm_arch_get_supported_msr_feature(kvm_state,
6959 wi->msr.index);
6960 break;
6961 }
6962 } else if (hvf_enabled()) {
6963 if (wi->type != CPUID_FEATURE_WORD) {
6964 return 0;
6965 }
6966 r = hvf_get_supported_cpuid(wi->cpuid.eax,
6967 wi->cpuid.ecx,
6968 wi->cpuid.reg);
6969 } else if (tcg_enabled()) {
6970 r = wi->tcg_features;
6971 } else {
6972 return ~0;
6973 }
6974
6975 switch (w) {
6976 #ifndef TARGET_X86_64
6977 case FEAT_8000_0001_EDX:
6978 /*
6979 * 32-bit TCG can emulate 64-bit compatibility mode. If there is no
6980 * way for userspace to get out of its 32-bit jail, we can leave
6981 * the LM bit set.
6982 */
6983 unavail = tcg_enabled()
6984 ? CPUID_EXT2_LM & ~CPUID_EXT2_KERNEL_FEATURES
6985 : CPUID_EXT2_LM;
6986 break;
6987 #endif
6988
6989 case FEAT_8000_0007_EBX:
6990 if (cpu && !IS_AMD_CPU(&cpu->env)) {
6991 /* Disable AMD machine check architecture for Intel CPU. */
6992 unavail = ~0;
6993 }
6994 break;
6995
6996 case FEAT_7_0_EBX:
6997 #ifndef CONFIG_USER_ONLY
6998 if (!check_sgx_support()) {
6999 unavail = CPUID_7_0_EBX_SGX;
7000 }
7001 #endif
7002 break;
7003 case FEAT_7_0_ECX:
7004 #ifndef CONFIG_USER_ONLY
7005 if (!check_sgx_support()) {
7006 unavail = CPUID_7_0_ECX_SGX_LC;
7007 }
7008 #endif
7009 break;
7010
7011 default:
7012 break;
7013 }
7014
7015 r &= ~unavail;
7016 if (cpu && cpu->migratable) {
7017 r &= x86_cpu_get_migratable_flags(cpu, w);
7018 }
7019 return r;
7020 }
7021
x86_cpu_get_supported_cpuid(uint32_t func,uint32_t index,uint32_t * eax,uint32_t * ebx,uint32_t * ecx,uint32_t * edx)7022 static void x86_cpu_get_supported_cpuid(uint32_t func, uint32_t index,
7023 uint32_t *eax, uint32_t *ebx,
7024 uint32_t *ecx, uint32_t *edx)
7025 {
7026 if (kvm_enabled()) {
7027 *eax = kvm_arch_get_supported_cpuid(kvm_state, func, index, R_EAX);
7028 *ebx = kvm_arch_get_supported_cpuid(kvm_state, func, index, R_EBX);
7029 *ecx = kvm_arch_get_supported_cpuid(kvm_state, func, index, R_ECX);
7030 *edx = kvm_arch_get_supported_cpuid(kvm_state, func, index, R_EDX);
7031 } else if (hvf_enabled()) {
7032 *eax = hvf_get_supported_cpuid(func, index, R_EAX);
7033 *ebx = hvf_get_supported_cpuid(func, index, R_EBX);
7034 *ecx = hvf_get_supported_cpuid(func, index, R_ECX);
7035 *edx = hvf_get_supported_cpuid(func, index, R_EDX);
7036 } else {
7037 *eax = 0;
7038 *ebx = 0;
7039 *ecx = 0;
7040 *edx = 0;
7041 }
7042 }
7043
x86_cpu_get_cache_cpuid(uint32_t func,uint32_t index,uint32_t * eax,uint32_t * ebx,uint32_t * ecx,uint32_t * edx)7044 static void x86_cpu_get_cache_cpuid(uint32_t func, uint32_t index,
7045 uint32_t *eax, uint32_t *ebx,
7046 uint32_t *ecx, uint32_t *edx)
7047 {
7048 uint32_t level, unused;
7049
7050 /* Only return valid host leaves. */
7051 switch (func) {
7052 case 2:
7053 case 4:
7054 host_cpuid(0, 0, &level, &unused, &unused, &unused);
7055 break;
7056 case 0x80000005:
7057 case 0x80000006:
7058 case 0x8000001d:
7059 host_cpuid(0x80000000, 0, &level, &unused, &unused, &unused);
7060 break;
7061 default:
7062 return;
7063 }
7064
7065 if (func > level) {
7066 *eax = 0;
7067 *ebx = 0;
7068 *ecx = 0;
7069 *edx = 0;
7070 } else {
7071 host_cpuid(func, index, eax, ebx, ecx, edx);
7072 }
7073 }
7074
7075 /*
7076 * Only for builtin_x86_defs models initialized with x86_register_cpudef_types.
7077 */
x86_cpu_apply_props(X86CPU * cpu,PropValue * props)7078 void x86_cpu_apply_props(X86CPU *cpu, PropValue *props)
7079 {
7080 PropValue *pv;
7081 for (pv = props; pv->prop; pv++) {
7082 if (!pv->value) {
7083 continue;
7084 }
7085 object_property_parse(OBJECT(cpu), pv->prop, pv->value,
7086 &error_abort);
7087 }
7088 }
7089
7090 /*
7091 * Apply properties for the CPU model version specified in model.
7092 * Only for builtin_x86_defs models initialized with x86_register_cpudef_types.
7093 */
7094
x86_cpu_apply_version_props(X86CPU * cpu,const X86CPUModel * model)7095 static void x86_cpu_apply_version_props(X86CPU *cpu, const X86CPUModel *model)
7096 {
7097 const X86CPUVersionDefinition *vdef;
7098 X86CPUVersion version = x86_cpu_model_resolve_version(model);
7099
7100 if (version == CPU_VERSION_LEGACY) {
7101 return;
7102 }
7103
7104 for (vdef = x86_cpu_def_get_versions(model->cpudef); vdef->version; vdef++) {
7105 PropValue *p;
7106
7107 for (p = vdef->props; p && p->prop; p++) {
7108 object_property_parse(OBJECT(cpu), p->prop, p->value,
7109 &error_abort);
7110 }
7111
7112 if (vdef->version == version) {
7113 break;
7114 }
7115 }
7116
7117 /*
7118 * If we reached the end of the list, version number was invalid
7119 */
7120 assert(vdef->version == version);
7121 }
7122
x86_cpu_get_versioned_cache_info(X86CPU * cpu,const X86CPUModel * model)7123 static const CPUCaches *x86_cpu_get_versioned_cache_info(X86CPU *cpu,
7124 const X86CPUModel *model)
7125 {
7126 const X86CPUVersionDefinition *vdef;
7127 X86CPUVersion version = x86_cpu_model_resolve_version(model);
7128 const CPUCaches *cache_info = model->cpudef->cache_info;
7129
7130 if (version == CPU_VERSION_LEGACY) {
7131 return cache_info;
7132 }
7133
7134 for (vdef = x86_cpu_def_get_versions(model->cpudef); vdef->version; vdef++) {
7135 if (vdef->cache_info) {
7136 cache_info = vdef->cache_info;
7137 }
7138
7139 if (vdef->version == version) {
7140 break;
7141 }
7142 }
7143
7144 assert(vdef->version == version);
7145 return cache_info;
7146 }
7147
7148 /*
7149 * Load data from X86CPUDefinition into a X86CPU object.
7150 * Only for builtin_x86_defs models initialized with x86_register_cpudef_types.
7151 */
x86_cpu_load_model(X86CPU * cpu,const X86CPUModel * model)7152 static void x86_cpu_load_model(X86CPU *cpu, const X86CPUModel *model)
7153 {
7154 const X86CPUDefinition *def = model->cpudef;
7155 CPUX86State *env = &cpu->env;
7156 FeatureWord w;
7157
7158 /*NOTE: any property set by this function should be returned by
7159 * x86_cpu_static_props(), so static expansion of
7160 * query-cpu-model-expansion is always complete.
7161 */
7162
7163 /* CPU models only set _minimum_ values for level/xlevel: */
7164 object_property_set_uint(OBJECT(cpu), "min-level", def->level,
7165 &error_abort);
7166 object_property_set_uint(OBJECT(cpu), "min-xlevel", def->xlevel,
7167 &error_abort);
7168
7169 object_property_set_int(OBJECT(cpu), "family", def->family, &error_abort);
7170 object_property_set_int(OBJECT(cpu), "model", def->model, &error_abort);
7171 object_property_set_int(OBJECT(cpu), "stepping", def->stepping,
7172 &error_abort);
7173 object_property_set_str(OBJECT(cpu), "model-id", def->model_id,
7174 &error_abort);
7175 for (w = 0; w < FEATURE_WORDS; w++) {
7176 env->features[w] = def->features[w];
7177 }
7178
7179 /* legacy-cache defaults to 'off' if CPU model provides cache info */
7180 cpu->legacy_cache = !x86_cpu_get_versioned_cache_info(cpu, model);
7181
7182 env->features[FEAT_1_ECX] |= CPUID_EXT_HYPERVISOR;
7183
7184 /* sysenter isn't supported in compatibility mode on AMD,
7185 * syscall isn't supported in compatibility mode on Intel.
7186 * Normally we advertise the actual CPU vendor, but you can
7187 * override this using the 'vendor' property if you want to use
7188 * KVM's sysenter/syscall emulation in compatibility mode and
7189 * when doing cross vendor migration
7190 */
7191
7192 /*
7193 * vendor property is set here but then overloaded with the
7194 * host cpu vendor for KVM and HVF.
7195 */
7196 object_property_set_str(OBJECT(cpu), "vendor", def->vendor, &error_abort);
7197
7198 object_property_set_uint(OBJECT(cpu), "avx10-version", def->avx10_version,
7199 &error_abort);
7200
7201 x86_cpu_apply_version_props(cpu, model);
7202
7203 /*
7204 * Properties in versioned CPU model are not user specified features.
7205 * We can simply clear env->user_features here since it will be filled later
7206 * in x86_cpu_expand_features() based on plus_features and minus_features.
7207 */
7208 memset(&env->user_features, 0, sizeof(env->user_features));
7209 }
7210
x86_gdb_arch_name(CPUState * cs)7211 static const gchar *x86_gdb_arch_name(CPUState *cs)
7212 {
7213 #ifdef TARGET_X86_64
7214 return "i386:x86-64";
7215 #else
7216 return "i386";
7217 #endif
7218 }
7219
x86_cpu_cpudef_class_init(ObjectClass * oc,const void * data)7220 static void x86_cpu_cpudef_class_init(ObjectClass *oc, const void *data)
7221 {
7222 const X86CPUModel *model = data;
7223 X86CPUClass *xcc = X86_CPU_CLASS(oc);
7224 CPUClass *cc = CPU_CLASS(oc);
7225
7226 xcc->model = model;
7227 xcc->migration_safe = true;
7228 cc->deprecation_note = model->cpudef->deprecation_note;
7229 }
7230
x86_register_cpu_model_type(const char * name,X86CPUModel * model)7231 static void x86_register_cpu_model_type(const char *name, X86CPUModel *model)
7232 {
7233 g_autofree char *typename = x86_cpu_type_name(name);
7234 TypeInfo ti = {
7235 .name = typename,
7236 .parent = TYPE_X86_CPU,
7237 .class_init = x86_cpu_cpudef_class_init,
7238 .class_data = model,
7239 };
7240
7241 type_register_static(&ti);
7242 }
7243
7244
7245 /*
7246 * register builtin_x86_defs;
7247 * "max", "base" and subclasses ("host") are not registered here.
7248 * See x86_cpu_register_types for all model registrations.
7249 */
x86_register_cpudef_types(const X86CPUDefinition * def)7250 static void x86_register_cpudef_types(const X86CPUDefinition *def)
7251 {
7252 X86CPUModel *m;
7253 const X86CPUVersionDefinition *vdef;
7254
7255 /* AMD aliases are handled at runtime based on CPUID vendor, so
7256 * they shouldn't be set on the CPU model table.
7257 */
7258 assert(!(def->features[FEAT_8000_0001_EDX] & CPUID_EXT2_AMD_ALIASES));
7259 /* catch mistakes instead of silently truncating model_id when too long */
7260 assert(def->model_id && strlen(def->model_id) <= 48);
7261
7262 /* Unversioned model: */
7263 m = g_new0(X86CPUModel, 1);
7264 m->cpudef = def;
7265 m->version = CPU_VERSION_AUTO;
7266 m->is_alias = true;
7267 x86_register_cpu_model_type(def->name, m);
7268
7269 /* Versioned models: */
7270
7271 for (vdef = x86_cpu_def_get_versions(def); vdef->version; vdef++) {
7272 g_autofree char *name =
7273 x86_cpu_versioned_model_name(def, vdef->version);
7274
7275 m = g_new0(X86CPUModel, 1);
7276 m->cpudef = def;
7277 m->version = vdef->version;
7278 m->note = vdef->note;
7279 x86_register_cpu_model_type(name, m);
7280
7281 if (vdef->alias) {
7282 X86CPUModel *am = g_new0(X86CPUModel, 1);
7283 am->cpudef = def;
7284 am->version = vdef->version;
7285 am->is_alias = true;
7286 x86_register_cpu_model_type(vdef->alias, am);
7287 }
7288 }
7289
7290 }
7291
cpu_x86_virtual_addr_width(CPUX86State * env)7292 uint32_t cpu_x86_virtual_addr_width(CPUX86State *env)
7293 {
7294 if (env->features[FEAT_7_0_ECX] & CPUID_7_0_ECX_LA57) {
7295 return 57; /* 57 bits virtual */
7296 } else {
7297 return 48; /* 48 bits virtual */
7298 }
7299 }
7300
cpu_x86_cpuid(CPUX86State * env,uint32_t index,uint32_t count,uint32_t * eax,uint32_t * ebx,uint32_t * ecx,uint32_t * edx)7301 void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count,
7302 uint32_t *eax, uint32_t *ebx,
7303 uint32_t *ecx, uint32_t *edx)
7304 {
7305 X86CPU *cpu = env_archcpu(env);
7306 CPUState *cs = env_cpu(env);
7307 uint32_t limit;
7308 uint32_t signature[3];
7309 X86CPUTopoInfo *topo_info = &env->topo_info;
7310 uint32_t threads_per_pkg;
7311
7312 threads_per_pkg = x86_threads_per_pkg(topo_info);
7313
7314 /* Calculate & apply limits for different index ranges */
7315 if (index >= 0xC0000000) {
7316 limit = env->cpuid_xlevel2;
7317 } else if (index >= 0x80000000) {
7318 limit = env->cpuid_xlevel;
7319 } else if (index >= 0x40000000) {
7320 limit = 0x40000001;
7321 } else {
7322 limit = env->cpuid_level;
7323 }
7324
7325 if (index > limit) {
7326 /* Intel documentation states that invalid EAX input will
7327 * return the same information as EAX=cpuid_level
7328 * (Intel SDM Vol. 2A - Instruction Set Reference - CPUID)
7329 */
7330 index = env->cpuid_level;
7331 }
7332
7333 switch(index) {
7334 case 0:
7335 *eax = env->cpuid_level;
7336 *ebx = env->cpuid_vendor1;
7337 *edx = env->cpuid_vendor2;
7338 *ecx = env->cpuid_vendor3;
7339 break;
7340 case 1:
7341 *eax = env->cpuid_version;
7342 *ebx = (cpu->apic_id << 24) |
7343 8 << 8; /* CLFLUSH size in quad words, Linux wants it. */
7344 *ecx = env->features[FEAT_1_ECX];
7345 if ((*ecx & CPUID_EXT_XSAVE) && (env->cr[4] & CR4_OSXSAVE_MASK)) {
7346 *ecx |= CPUID_EXT_OSXSAVE;
7347 }
7348 *edx = env->features[FEAT_1_EDX];
7349 if (threads_per_pkg > 1) {
7350 *ebx |= threads_per_pkg << 16;
7351 }
7352 if (!cpu->enable_pmu) {
7353 *ecx &= ~CPUID_EXT_PDCM;
7354 }
7355 break;
7356 case 2:
7357 /* cache info: needed for Pentium Pro compatibility */
7358 if (cpu->cache_info_passthrough) {
7359 x86_cpu_get_cache_cpuid(index, 0, eax, ebx, ecx, edx);
7360 break;
7361 } else if (cpu->vendor_cpuid_only && IS_AMD_CPU(env)) {
7362 *eax = *ebx = *ecx = *edx = 0;
7363 break;
7364 }
7365 *eax = 1; /* Number of CPUID[EAX=2] calls required */
7366 *ebx = 0;
7367 if (!cpu->enable_l3_cache) {
7368 *ecx = 0;
7369 } else {
7370 *ecx = cpuid2_cache_descriptor(env->cache_info_cpuid2.l3_cache);
7371 }
7372 *edx = (cpuid2_cache_descriptor(env->cache_info_cpuid2.l1d_cache) << 16) |
7373 (cpuid2_cache_descriptor(env->cache_info_cpuid2.l1i_cache) << 8) |
7374 (cpuid2_cache_descriptor(env->cache_info_cpuid2.l2_cache));
7375 break;
7376 case 4:
7377 /* cache info: needed for Core compatibility */
7378 if (cpu->cache_info_passthrough) {
7379 x86_cpu_get_cache_cpuid(index, count, eax, ebx, ecx, edx);
7380 /*
7381 * QEMU has its own number of cores/logical cpus,
7382 * set 24..14, 31..26 bit to configured values
7383 */
7384 if (*eax & 31) {
7385 int host_vcpus_per_cache = 1 + ((*eax & 0x3FFC000) >> 14);
7386
7387 *eax &= ~0xFC000000;
7388 *eax |= max_core_ids_in_package(topo_info) << 26;
7389 if (host_vcpus_per_cache > threads_per_pkg) {
7390 *eax &= ~0x3FFC000;
7391
7392 /* Share the cache at package level. */
7393 *eax |= max_thread_ids_for_cache(topo_info,
7394 CPU_TOPOLOGY_LEVEL_SOCKET) << 14;
7395 }
7396 }
7397 } else if (cpu->vendor_cpuid_only && IS_AMD_CPU(env)) {
7398 *eax = *ebx = *ecx = *edx = 0;
7399 } else {
7400 *eax = 0;
7401
7402 switch (count) {
7403 case 0: /* L1 dcache info */
7404 encode_cache_cpuid4(env->cache_info_cpuid4.l1d_cache,
7405 topo_info,
7406 eax, ebx, ecx, edx);
7407 if (!cpu->l1_cache_per_core) {
7408 *eax &= ~MAKE_64BIT_MASK(14, 12);
7409 }
7410 break;
7411 case 1: /* L1 icache info */
7412 encode_cache_cpuid4(env->cache_info_cpuid4.l1i_cache,
7413 topo_info,
7414 eax, ebx, ecx, edx);
7415 if (!cpu->l1_cache_per_core) {
7416 *eax &= ~MAKE_64BIT_MASK(14, 12);
7417 }
7418 break;
7419 case 2: /* L2 cache info */
7420 encode_cache_cpuid4(env->cache_info_cpuid4.l2_cache,
7421 topo_info,
7422 eax, ebx, ecx, edx);
7423 break;
7424 case 3: /* L3 cache info */
7425 if (cpu->enable_l3_cache) {
7426 encode_cache_cpuid4(env->cache_info_cpuid4.l3_cache,
7427 topo_info,
7428 eax, ebx, ecx, edx);
7429 break;
7430 }
7431 /* fall through */
7432 default: /* end of info */
7433 *eax = *ebx = *ecx = *edx = 0;
7434 break;
7435 }
7436 }
7437 break;
7438 case 5:
7439 /* MONITOR/MWAIT Leaf */
7440 *eax = cpu->mwait.eax; /* Smallest monitor-line size in bytes */
7441 *ebx = cpu->mwait.ebx; /* Largest monitor-line size in bytes */
7442 *ecx = cpu->mwait.ecx; /* flags */
7443 *edx = cpu->mwait.edx; /* mwait substates */
7444 break;
7445 case 6:
7446 /* Thermal and Power Leaf */
7447 *eax = env->features[FEAT_6_EAX];
7448 *ebx = 0;
7449 *ecx = 0;
7450 *edx = 0;
7451 break;
7452 case 7:
7453 /* Structured Extended Feature Flags Enumeration Leaf */
7454 if (count == 0) {
7455 /* Maximum ECX value for sub-leaves */
7456 *eax = env->cpuid_level_func7;
7457 *ebx = env->features[FEAT_7_0_EBX]; /* Feature flags */
7458 *ecx = env->features[FEAT_7_0_ECX]; /* Feature flags */
7459 if ((*ecx & CPUID_7_0_ECX_PKU) && env->cr[4] & CR4_PKE_MASK) {
7460 *ecx |= CPUID_7_0_ECX_OSPKE;
7461 }
7462 *edx = env->features[FEAT_7_0_EDX]; /* Feature flags */
7463 } else if (count == 1) {
7464 *eax = env->features[FEAT_7_1_EAX];
7465 *ecx = env->features[FEAT_7_1_ECX];
7466 *edx = env->features[FEAT_7_1_EDX];
7467 *ebx = 0;
7468 } else if (count == 2) {
7469 *edx = env->features[FEAT_7_2_EDX];
7470 *eax = 0;
7471 *ebx = 0;
7472 *ecx = 0;
7473 } else {
7474 *eax = 0;
7475 *ebx = 0;
7476 *ecx = 0;
7477 *edx = 0;
7478 }
7479 break;
7480 case 9:
7481 /* Direct Cache Access Information Leaf */
7482 *eax = 0; /* Bits 0-31 in DCA_CAP MSR */
7483 *ebx = 0;
7484 *ecx = 0;
7485 *edx = 0;
7486 break;
7487 case 0xA:
7488 /* Architectural Performance Monitoring Leaf */
7489 if (cpu->enable_pmu) {
7490 x86_cpu_get_supported_cpuid(0xA, count, eax, ebx, ecx, edx);
7491 } else {
7492 *eax = 0;
7493 *ebx = 0;
7494 *ecx = 0;
7495 *edx = 0;
7496 }
7497 break;
7498 case 0xB:
7499 /* Extended Topology Enumeration Leaf */
7500 if (!cpu->enable_cpuid_0xb) {
7501 *eax = *ebx = *ecx = *edx = 0;
7502 break;
7503 }
7504
7505 *ecx = count & 0xff;
7506 *edx = cpu->apic_id;
7507
7508 switch (count) {
7509 case 0:
7510 *eax = apicid_core_offset(topo_info);
7511 *ebx = topo_info->threads_per_core;
7512 *ecx |= CPUID_B_ECX_TOPO_LEVEL_SMT << 8;
7513 break;
7514 case 1:
7515 *eax = apicid_pkg_offset(topo_info);
7516 *ebx = threads_per_pkg;
7517 *ecx |= CPUID_B_ECX_TOPO_LEVEL_CORE << 8;
7518 break;
7519 default:
7520 *eax = 0;
7521 *ebx = 0;
7522 *ecx |= CPUID_B_ECX_TOPO_LEVEL_INVALID << 8;
7523 }
7524
7525 assert(!(*eax & ~0x1f));
7526 *ebx &= 0xffff; /* The count doesn't need to be reliable. */
7527 break;
7528 case 0x1C:
7529 if (cpu->enable_pmu && (env->features[FEAT_7_0_EDX] & CPUID_7_0_EDX_ARCH_LBR)) {
7530 x86_cpu_get_supported_cpuid(0x1C, 0, eax, ebx, ecx, edx);
7531 *edx = 0;
7532 }
7533 break;
7534 case 0x1F:
7535 /* V2 Extended Topology Enumeration Leaf */
7536 if (!x86_has_cpuid_0x1f(cpu)) {
7537 *eax = *ebx = *ecx = *edx = 0;
7538 break;
7539 }
7540
7541 encode_topo_cpuid1f(env, count, topo_info, eax, ebx, ecx, edx);
7542 break;
7543 case 0xD: {
7544 /* Processor Extended State */
7545 *eax = 0;
7546 *ebx = 0;
7547 *ecx = 0;
7548 *edx = 0;
7549 if (!(env->features[FEAT_1_ECX] & CPUID_EXT_XSAVE)) {
7550 break;
7551 }
7552
7553 if (count == 0) {
7554 *ecx = xsave_area_size(x86_cpu_xsave_xcr0_components(cpu), false);
7555 *eax = env->features[FEAT_XSAVE_XCR0_LO];
7556 *edx = env->features[FEAT_XSAVE_XCR0_HI];
7557 /*
7558 * The initial value of xcr0 and ebx == 0, On host without kvm
7559 * commit 412a3c41(e.g., CentOS 6), the ebx's value always == 0
7560 * even through guest update xcr0, this will crash some legacy guest
7561 * (e.g., CentOS 6), So set ebx == ecx to workaround it.
7562 */
7563 *ebx = kvm_enabled() ? *ecx : xsave_area_size(env->xcr0, false);
7564 } else if (count == 1) {
7565 uint64_t xstate = x86_cpu_xsave_xcr0_components(cpu) |
7566 x86_cpu_xsave_xss_components(cpu);
7567
7568 *eax = env->features[FEAT_XSAVE];
7569 *ebx = xsave_area_size(xstate, true);
7570 *ecx = env->features[FEAT_XSAVE_XSS_LO];
7571 *edx = env->features[FEAT_XSAVE_XSS_HI];
7572 if (kvm_enabled() && cpu->enable_pmu &&
7573 (env->features[FEAT_7_0_EDX] & CPUID_7_0_EDX_ARCH_LBR) &&
7574 (*eax & CPUID_XSAVE_XSAVES)) {
7575 *ecx |= XSTATE_ARCH_LBR_MASK;
7576 } else {
7577 *ecx &= ~XSTATE_ARCH_LBR_MASK;
7578 }
7579 } else if (count == 0xf && cpu->enable_pmu
7580 && (env->features[FEAT_7_0_EDX] & CPUID_7_0_EDX_ARCH_LBR)) {
7581 x86_cpu_get_supported_cpuid(0xD, count, eax, ebx, ecx, edx);
7582 } else if (count < ARRAY_SIZE(x86_ext_save_areas)) {
7583 const ExtSaveArea *esa = &x86_ext_save_areas[count];
7584
7585 if (x86_cpu_xsave_xcr0_components(cpu) & (1ULL << count)) {
7586 *eax = esa->size;
7587 *ebx = esa->offset;
7588 *ecx = esa->ecx &
7589 (ESA_FEATURE_ALIGN64_MASK | ESA_FEATURE_XFD_MASK);
7590 } else if (x86_cpu_xsave_xss_components(cpu) & (1ULL << count)) {
7591 *eax = esa->size;
7592 *ebx = 0;
7593 *ecx = 1;
7594 }
7595 }
7596 break;
7597 }
7598 case 0x12:
7599 #ifndef CONFIG_USER_ONLY
7600 if (!kvm_enabled() ||
7601 !(env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_SGX)) {
7602 *eax = *ebx = *ecx = *edx = 0;
7603 break;
7604 }
7605
7606 /*
7607 * SGX sub-leafs CPUID.0x12.{0x2..N} enumerate EPC sections. Retrieve
7608 * the EPC properties, e.g. confidentiality and integrity, from the
7609 * host's first EPC section, i.e. assume there is one EPC section or
7610 * that all EPC sections have the same security properties.
7611 */
7612 if (count > 1) {
7613 uint64_t epc_addr, epc_size;
7614
7615 if (sgx_epc_get_section(count - 2, &epc_addr, &epc_size)) {
7616 *eax = *ebx = *ecx = *edx = 0;
7617 break;
7618 }
7619 host_cpuid(index, 2, eax, ebx, ecx, edx);
7620 *eax = (uint32_t)(epc_addr & 0xfffff000) | 0x1;
7621 *ebx = (uint32_t)(epc_addr >> 32);
7622 *ecx = (uint32_t)(epc_size & 0xfffff000) | (*ecx & 0xf);
7623 *edx = (uint32_t)(epc_size >> 32);
7624 break;
7625 }
7626
7627 /*
7628 * SGX sub-leafs CPUID.0x12.{0x0,0x1} are heavily dependent on hardware
7629 * and KVM, i.e. QEMU cannot emulate features to override what KVM
7630 * supports. Features can be further restricted by userspace, but not
7631 * made more permissive.
7632 */
7633 x86_cpu_get_supported_cpuid(0x12, count, eax, ebx, ecx, edx);
7634
7635 if (count == 0) {
7636 *eax &= env->features[FEAT_SGX_12_0_EAX];
7637 *ebx &= env->features[FEAT_SGX_12_0_EBX];
7638 } else {
7639 *eax &= env->features[FEAT_SGX_12_1_EAX];
7640 *ebx &= 0; /* ebx reserve */
7641 *ecx &= env->features[FEAT_XSAVE_XCR0_LO];
7642 *edx &= env->features[FEAT_XSAVE_XCR0_HI];
7643
7644 /* FP and SSE are always allowed regardless of XSAVE/XCR0. */
7645 *ecx |= XSTATE_FP_MASK | XSTATE_SSE_MASK;
7646
7647 /* Access to PROVISIONKEY requires additional credentials. */
7648 if ((*eax & (1U << 4)) &&
7649 !kvm_enable_sgx_provisioning(cs->kvm_state)) {
7650 *eax &= ~(1U << 4);
7651 }
7652 }
7653 #endif
7654 break;
7655 case 0x14: {
7656 /* Intel Processor Trace Enumeration */
7657 *eax = 0;
7658 *ebx = 0;
7659 *ecx = 0;
7660 *edx = 0;
7661 if (!(env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_INTEL_PT) ||
7662 !kvm_enabled()) {
7663 break;
7664 }
7665
7666 /*
7667 * If these are changed, they should stay in sync with
7668 * x86_cpu_filter_features().
7669 */
7670 if (count == 0) {
7671 *eax = INTEL_PT_MAX_SUBLEAF;
7672 *ebx = INTEL_PT_MINIMAL_EBX;
7673 *ecx = INTEL_PT_MINIMAL_ECX;
7674 if (env->features[FEAT_14_0_ECX] & CPUID_14_0_ECX_LIP) {
7675 *ecx |= CPUID_14_0_ECX_LIP;
7676 }
7677 } else if (count == 1) {
7678 *eax = INTEL_PT_MTC_BITMAP | INTEL_PT_ADDR_RANGES_NUM;
7679 *ebx = INTEL_PT_PSB_BITMAP | INTEL_PT_CYCLE_BITMAP;
7680 }
7681 break;
7682 }
7683 case 0x1D: {
7684 /* AMX TILE, for now hardcoded for Sapphire Rapids*/
7685 *eax = 0;
7686 *ebx = 0;
7687 *ecx = 0;
7688 *edx = 0;
7689 if (!(env->features[FEAT_7_0_EDX] & CPUID_7_0_EDX_AMX_TILE)) {
7690 break;
7691 }
7692
7693 if (count == 0) {
7694 /* Highest numbered palette subleaf */
7695 *eax = INTEL_AMX_TILE_MAX_SUBLEAF;
7696 } else if (count == 1) {
7697 *eax = INTEL_AMX_TOTAL_TILE_BYTES |
7698 (INTEL_AMX_BYTES_PER_TILE << 16);
7699 *ebx = INTEL_AMX_BYTES_PER_ROW | (INTEL_AMX_TILE_MAX_NAMES << 16);
7700 *ecx = INTEL_AMX_TILE_MAX_ROWS;
7701 }
7702 break;
7703 }
7704 case 0x1E: {
7705 /* AMX TMUL, for now hardcoded for Sapphire Rapids */
7706 *eax = 0;
7707 *ebx = 0;
7708 *ecx = 0;
7709 *edx = 0;
7710 if (!(env->features[FEAT_7_0_EDX] & CPUID_7_0_EDX_AMX_TILE)) {
7711 break;
7712 }
7713
7714 if (count == 0) {
7715 /* Highest numbered palette subleaf */
7716 *ebx = INTEL_AMX_TMUL_MAX_K | (INTEL_AMX_TMUL_MAX_N << 8);
7717 }
7718 break;
7719 }
7720 case 0x24: {
7721 *eax = 0;
7722 *ebx = 0;
7723 *ecx = 0;
7724 *edx = 0;
7725 if ((env->features[FEAT_7_1_EDX] & CPUID_7_1_EDX_AVX10) && count == 0) {
7726 *ebx = env->features[FEAT_24_0_EBX] | env->avx10_version;
7727 }
7728 break;
7729 }
7730 case 0x40000000:
7731 /*
7732 * CPUID code in kvm_arch_init_vcpu() ignores stuff
7733 * set here, but we restrict to TCG none the less.
7734 */
7735 if (tcg_enabled() && cpu->expose_tcg) {
7736 memcpy(signature, "TCGTCGTCGTCG", 12);
7737 *eax = 0x40000001;
7738 *ebx = signature[0];
7739 *ecx = signature[1];
7740 *edx = signature[2];
7741 } else {
7742 *eax = 0;
7743 *ebx = 0;
7744 *ecx = 0;
7745 *edx = 0;
7746 }
7747 break;
7748 case 0x40000001:
7749 *eax = 0;
7750 *ebx = 0;
7751 *ecx = 0;
7752 *edx = 0;
7753 break;
7754 case 0x80000000:
7755 *eax = env->cpuid_xlevel;
7756 *ebx = env->cpuid_vendor1;
7757 *edx = env->cpuid_vendor2;
7758 *ecx = env->cpuid_vendor3;
7759 break;
7760 case 0x80000001:
7761 *eax = env->cpuid_version;
7762 *ebx = 0;
7763 *ecx = env->features[FEAT_8000_0001_ECX];
7764 *edx = env->features[FEAT_8000_0001_EDX];
7765
7766 if (tcg_enabled() && env->cpuid_vendor1 == CPUID_VENDOR_INTEL_1 &&
7767 !(env->hflags & HF_LMA_MASK)) {
7768 *edx &= ~CPUID_EXT2_SYSCALL;
7769 }
7770 break;
7771 case 0x80000002:
7772 case 0x80000003:
7773 case 0x80000004:
7774 *eax = env->cpuid_model[(index - 0x80000002) * 4 + 0];
7775 *ebx = env->cpuid_model[(index - 0x80000002) * 4 + 1];
7776 *ecx = env->cpuid_model[(index - 0x80000002) * 4 + 2];
7777 *edx = env->cpuid_model[(index - 0x80000002) * 4 + 3];
7778 break;
7779 case 0x80000005:
7780 /* cache info (L1 cache) */
7781 if (cpu->cache_info_passthrough) {
7782 x86_cpu_get_cache_cpuid(index, 0, eax, ebx, ecx, edx);
7783 break;
7784 }
7785 *eax = (L1_DTLB_2M_ASSOC << 24) | (L1_DTLB_2M_ENTRIES << 16) |
7786 (L1_ITLB_2M_ASSOC << 8) | (L1_ITLB_2M_ENTRIES);
7787 *ebx = (L1_DTLB_4K_ASSOC << 24) | (L1_DTLB_4K_ENTRIES << 16) |
7788 (L1_ITLB_4K_ASSOC << 8) | (L1_ITLB_4K_ENTRIES);
7789 *ecx = encode_cache_cpuid80000005(env->cache_info_amd.l1d_cache);
7790 *edx = encode_cache_cpuid80000005(env->cache_info_amd.l1i_cache);
7791 break;
7792 case 0x80000006:
7793 /* cache info (L2 cache) */
7794 if (cpu->cache_info_passthrough) {
7795 x86_cpu_get_cache_cpuid(index, 0, eax, ebx, ecx, edx);
7796 break;
7797 }
7798 *eax = (AMD_ENC_ASSOC(L2_DTLB_2M_ASSOC) << 28) |
7799 (L2_DTLB_2M_ENTRIES << 16) |
7800 (AMD_ENC_ASSOC(L2_ITLB_2M_ASSOC) << 12) |
7801 (L2_ITLB_2M_ENTRIES);
7802 *ebx = (AMD_ENC_ASSOC(L2_DTLB_4K_ASSOC) << 28) |
7803 (L2_DTLB_4K_ENTRIES << 16) |
7804 (AMD_ENC_ASSOC(L2_ITLB_4K_ASSOC) << 12) |
7805 (L2_ITLB_4K_ENTRIES);
7806 encode_cache_cpuid80000006(env->cache_info_amd.l2_cache,
7807 cpu->enable_l3_cache ?
7808 env->cache_info_amd.l3_cache : NULL,
7809 ecx, edx);
7810 break;
7811 case 0x80000007:
7812 *eax = 0;
7813 *ebx = env->features[FEAT_8000_0007_EBX];
7814 *ecx = 0;
7815 *edx = env->features[FEAT_8000_0007_EDX];
7816 break;
7817 case 0x80000008:
7818 /* virtual & phys address size in low 2 bytes. */
7819 *eax = cpu->phys_bits;
7820 if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_LM) {
7821 /* 64 bit processor */
7822 *eax |= (cpu_x86_virtual_addr_width(env) << 8);
7823 *eax |= (cpu->guest_phys_bits << 16);
7824 }
7825 *ebx = env->features[FEAT_8000_0008_EBX];
7826 if (threads_per_pkg > 1) {
7827 /*
7828 * Bits 15:12 is "The number of bits in the initial
7829 * Core::X86::Apic::ApicId[ApicId] value that indicate
7830 * thread ID within a package".
7831 * Bits 7:0 is "The number of threads in the package is NC+1"
7832 */
7833 *ecx = (apicid_pkg_offset(topo_info) << 12) |
7834 (threads_per_pkg - 1);
7835 } else {
7836 *ecx = 0;
7837 }
7838 *edx = 0;
7839 break;
7840 case 0x8000000A:
7841 if (env->features[FEAT_8000_0001_ECX] & CPUID_EXT3_SVM) {
7842 *eax = 0x00000001; /* SVM Revision */
7843 *ebx = 0x00000010; /* nr of ASIDs */
7844 *ecx = 0;
7845 *edx = env->features[FEAT_SVM]; /* optional features */
7846 } else {
7847 *eax = 0;
7848 *ebx = 0;
7849 *ecx = 0;
7850 *edx = 0;
7851 }
7852 break;
7853 case 0x8000001D:
7854 *eax = 0;
7855 if (cpu->cache_info_passthrough) {
7856 x86_cpu_get_cache_cpuid(index, count, eax, ebx, ecx, edx);
7857 break;
7858 }
7859 switch (count) {
7860 case 0: /* L1 dcache info */
7861 encode_cache_cpuid8000001d(env->cache_info_amd.l1d_cache,
7862 topo_info, eax, ebx, ecx, edx);
7863 break;
7864 case 1: /* L1 icache info */
7865 encode_cache_cpuid8000001d(env->cache_info_amd.l1i_cache,
7866 topo_info, eax, ebx, ecx, edx);
7867 break;
7868 case 2: /* L2 cache info */
7869 encode_cache_cpuid8000001d(env->cache_info_amd.l2_cache,
7870 topo_info, eax, ebx, ecx, edx);
7871 break;
7872 case 3: /* L3 cache info */
7873 encode_cache_cpuid8000001d(env->cache_info_amd.l3_cache,
7874 topo_info, eax, ebx, ecx, edx);
7875 break;
7876 default: /* end of info */
7877 *eax = *ebx = *ecx = *edx = 0;
7878 break;
7879 }
7880 if (cpu->amd_topoext_features_only) {
7881 *edx &= CACHE_NO_INVD_SHARING | CACHE_INCLUSIVE;
7882 }
7883 break;
7884 case 0x8000001E:
7885 if (cpu->core_id <= 255) {
7886 encode_topo_cpuid8000001e(cpu, topo_info, eax, ebx, ecx, edx);
7887 } else {
7888 *eax = 0;
7889 *ebx = 0;
7890 *ecx = 0;
7891 *edx = 0;
7892 }
7893 break;
7894 case 0x80000022:
7895 *eax = *ebx = *ecx = *edx = 0;
7896 /* AMD Extended Performance Monitoring and Debug */
7897 if (kvm_enabled() && cpu->enable_pmu &&
7898 (env->features[FEAT_8000_0022_EAX] & CPUID_8000_0022_EAX_PERFMON_V2)) {
7899 *eax |= CPUID_8000_0022_EAX_PERFMON_V2;
7900 *ebx |= kvm_arch_get_supported_cpuid(cs->kvm_state, index, count,
7901 R_EBX) & 0xf;
7902 }
7903 break;
7904 case 0xC0000000:
7905 *eax = env->cpuid_xlevel2;
7906 *ebx = 0;
7907 *ecx = 0;
7908 *edx = 0;
7909 break;
7910 case 0xC0000001:
7911 /* Support for VIA CPU's CPUID instruction */
7912 *eax = env->cpuid_version;
7913 *ebx = 0;
7914 *ecx = 0;
7915 *edx = env->features[FEAT_C000_0001_EDX];
7916 break;
7917 case 0xC0000002:
7918 case 0xC0000003:
7919 case 0xC0000004:
7920 /* Reserved for the future, and now filled with zero */
7921 *eax = 0;
7922 *ebx = 0;
7923 *ecx = 0;
7924 *edx = 0;
7925 break;
7926 case 0x8000001F:
7927 *eax = *ebx = *ecx = *edx = 0;
7928 if (sev_enabled()) {
7929 *eax = 0x2;
7930 *eax |= sev_es_enabled() ? 0x8 : 0;
7931 *eax |= sev_snp_enabled() ? 0x10 : 0;
7932 *ebx = sev_get_cbit_position() & 0x3f; /* EBX[5:0] */
7933 *ebx |= (sev_get_reduced_phys_bits() & 0x3f) << 6; /* EBX[11:6] */
7934 }
7935 break;
7936 case 0x80000021:
7937 *eax = *ebx = *ecx = *edx = 0;
7938 *eax = env->features[FEAT_8000_0021_EAX];
7939 *ebx = env->features[FEAT_8000_0021_EBX];
7940 break;
7941 default:
7942 /* reserved values: zero */
7943 *eax = 0;
7944 *ebx = 0;
7945 *ecx = 0;
7946 *edx = 0;
7947 break;
7948 }
7949 }
7950
x86_cpu_set_sgxlepubkeyhash(CPUX86State * env)7951 static void x86_cpu_set_sgxlepubkeyhash(CPUX86State *env)
7952 {
7953 #ifndef CONFIG_USER_ONLY
7954 /* Those default values are defined in Skylake HW */
7955 env->msr_ia32_sgxlepubkeyhash[0] = 0xa6053e051270b7acULL;
7956 env->msr_ia32_sgxlepubkeyhash[1] = 0x6cfbe8ba8b3b413dULL;
7957 env->msr_ia32_sgxlepubkeyhash[2] = 0xc4916d99f2b3735dULL;
7958 env->msr_ia32_sgxlepubkeyhash[3] = 0xd4f8c05909f9bb3bULL;
7959 #endif
7960 }
7961
cpuid_has_xsave_feature(CPUX86State * env,const ExtSaveArea * esa)7962 static bool cpuid_has_xsave_feature(CPUX86State *env, const ExtSaveArea *esa)
7963 {
7964 if (!esa->size) {
7965 return false;
7966 }
7967
7968 if (env->features[esa->feature] & esa->bits) {
7969 return true;
7970 }
7971 if (esa->feature == FEAT_7_0_EBX && esa->bits == CPUID_7_0_EBX_AVX512F
7972 && (env->features[FEAT_7_1_EDX] & CPUID_7_1_EDX_AVX10)) {
7973 return true;
7974 }
7975
7976 return false;
7977 }
7978
x86_cpu_reset_hold(Object * obj,ResetType type)7979 static void x86_cpu_reset_hold(Object *obj, ResetType type)
7980 {
7981 CPUState *cs = CPU(obj);
7982 X86CPU *cpu = X86_CPU(cs);
7983 X86CPUClass *xcc = X86_CPU_GET_CLASS(obj);
7984 CPUX86State *env = &cpu->env;
7985 target_ulong cr4;
7986 uint64_t xcr0;
7987 int i;
7988
7989 if (xcc->parent_phases.hold) {
7990 xcc->parent_phases.hold(obj, type);
7991 }
7992
7993 memset(env, 0, offsetof(CPUX86State, end_reset_fields));
7994
7995 if (tcg_enabled()) {
7996 cpu_init_fp_statuses(env);
7997 }
7998
7999 env->old_exception = -1;
8000
8001 /* init to reset state */
8002 env->int_ctl = 0;
8003 env->hflags2 |= HF2_GIF_MASK;
8004 env->hflags2 |= HF2_VGIF_MASK;
8005 env->hflags &= ~HF_GUEST_MASK;
8006
8007 cpu_x86_update_cr0(env, 0x60000010);
8008 env->a20_mask = ~0x0;
8009 env->smbase = 0x30000;
8010 env->msr_smi_count = 0;
8011
8012 env->idt.limit = 0xffff;
8013 env->gdt.limit = 0xffff;
8014 env->ldt.limit = 0xffff;
8015 env->ldt.flags = DESC_P_MASK | (2 << DESC_TYPE_SHIFT);
8016 env->tr.limit = 0xffff;
8017 env->tr.flags = DESC_P_MASK | (11 << DESC_TYPE_SHIFT);
8018
8019 cpu_x86_load_seg_cache(env, R_CS, 0xf000, 0xffff0000, 0xffff,
8020 DESC_P_MASK | DESC_S_MASK | DESC_CS_MASK |
8021 DESC_R_MASK | DESC_A_MASK);
8022 cpu_x86_load_seg_cache(env, R_DS, 0, 0, 0xffff,
8023 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
8024 DESC_A_MASK);
8025 cpu_x86_load_seg_cache(env, R_ES, 0, 0, 0xffff,
8026 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
8027 DESC_A_MASK);
8028 cpu_x86_load_seg_cache(env, R_SS, 0, 0, 0xffff,
8029 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
8030 DESC_A_MASK);
8031 cpu_x86_load_seg_cache(env, R_FS, 0, 0, 0xffff,
8032 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
8033 DESC_A_MASK);
8034 cpu_x86_load_seg_cache(env, R_GS, 0, 0, 0xffff,
8035 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
8036 DESC_A_MASK);
8037
8038 env->eip = 0xfff0;
8039 env->regs[R_EDX] = env->cpuid_version;
8040
8041 env->eflags = 0x2;
8042
8043 /* FPU init */
8044 for (i = 0; i < 8; i++) {
8045 env->fptags[i] = 1;
8046 }
8047 cpu_set_fpuc(env, 0x37f);
8048
8049 env->mxcsr = 0x1f80;
8050 /* All units are in INIT state. */
8051 env->xstate_bv = 0;
8052
8053 env->pat = 0x0007040600070406ULL;
8054
8055 if (kvm_enabled()) {
8056 /*
8057 * KVM handles TSC = 0 specially and thinks we are hot-plugging
8058 * a new CPU, use 1 instead to force a reset.
8059 */
8060 if (env->tsc != 0) {
8061 env->tsc = 1;
8062 }
8063 } else {
8064 env->tsc = 0;
8065 }
8066
8067 env->msr_ia32_misc_enable = MSR_IA32_MISC_ENABLE_DEFAULT;
8068 if (env->features[FEAT_1_ECX] & CPUID_EXT_MONITOR) {
8069 env->msr_ia32_misc_enable |= MSR_IA32_MISC_ENABLE_MWAIT;
8070 }
8071
8072 memset(env->dr, 0, sizeof(env->dr));
8073 env->dr[6] = DR6_FIXED_1;
8074 env->dr[7] = DR7_FIXED_1;
8075 cpu_breakpoint_remove_all(cs, BP_CPU);
8076 cpu_watchpoint_remove_all(cs, BP_CPU);
8077
8078 cr4 = 0;
8079 xcr0 = XSTATE_FP_MASK;
8080
8081 #ifdef CONFIG_USER_ONLY
8082 /* Enable all the features for user-mode. */
8083 if (env->features[FEAT_1_EDX] & CPUID_SSE) {
8084 xcr0 |= XSTATE_SSE_MASK;
8085 }
8086 for (i = 2; i < ARRAY_SIZE(x86_ext_save_areas); i++) {
8087 const ExtSaveArea *esa = &x86_ext_save_areas[i];
8088 if (!((1 << i) & CPUID_XSTATE_XCR0_MASK)) {
8089 continue;
8090 }
8091 if (cpuid_has_xsave_feature(env, esa)) {
8092 xcr0 |= 1ull << i;
8093 }
8094 }
8095
8096 if (env->features[FEAT_1_ECX] & CPUID_EXT_XSAVE) {
8097 cr4 |= CR4_OSFXSR_MASK | CR4_OSXSAVE_MASK;
8098 }
8099 if (env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_FSGSBASE) {
8100 cr4 |= CR4_FSGSBASE_MASK;
8101 }
8102 #endif
8103
8104 env->xcr0 = xcr0;
8105 cpu_x86_update_cr4(env, cr4);
8106
8107 /*
8108 * SDM 11.11.5 requires:
8109 * - IA32_MTRR_DEF_TYPE MSR.E = 0
8110 * - IA32_MTRR_PHYSMASKn.V = 0
8111 * All other bits are undefined. For simplification, zero it all.
8112 */
8113 env->mtrr_deftype = 0;
8114 memset(env->mtrr_var, 0, sizeof(env->mtrr_var));
8115 memset(env->mtrr_fixed, 0, sizeof(env->mtrr_fixed));
8116
8117 env->interrupt_injected = -1;
8118 env->exception_nr = -1;
8119 env->exception_pending = 0;
8120 env->exception_injected = 0;
8121 env->exception_has_payload = false;
8122 env->exception_payload = 0;
8123 env->nmi_injected = false;
8124 env->triple_fault_pending = false;
8125 #if !defined(CONFIG_USER_ONLY)
8126 /* We hard-wire the BSP to the first CPU. */
8127 apic_designate_bsp(cpu->apic_state, cs->cpu_index == 0);
8128
8129 cs->halted = !cpu_is_bsp(cpu);
8130
8131 if (kvm_enabled()) {
8132 kvm_arch_reset_vcpu(cpu);
8133 }
8134
8135 x86_cpu_set_sgxlepubkeyhash(env);
8136
8137 env->amd_tsc_scale_msr = MSR_AMD64_TSC_RATIO_DEFAULT;
8138
8139 #endif
8140 }
8141
x86_cpu_after_reset(X86CPU * cpu)8142 void x86_cpu_after_reset(X86CPU *cpu)
8143 {
8144 #ifndef CONFIG_USER_ONLY
8145 if (kvm_enabled()) {
8146 kvm_arch_after_reset_vcpu(cpu);
8147 }
8148
8149 if (cpu->apic_state) {
8150 device_cold_reset(cpu->apic_state);
8151 }
8152 #endif
8153 }
8154
mce_init(X86CPU * cpu)8155 static void mce_init(X86CPU *cpu)
8156 {
8157 CPUX86State *cenv = &cpu->env;
8158 unsigned int bank;
8159
8160 if (((cenv->cpuid_version >> 8) & 0xf) >= 6
8161 && (cenv->features[FEAT_1_EDX] & (CPUID_MCE | CPUID_MCA)) ==
8162 (CPUID_MCE | CPUID_MCA)) {
8163 cenv->mcg_cap = MCE_CAP_DEF | MCE_BANKS_DEF |
8164 (cpu->enable_lmce ? MCG_LMCE_P : 0);
8165 cenv->mcg_ctl = ~(uint64_t)0;
8166 for (bank = 0; bank < MCE_BANKS_DEF; bank++) {
8167 cenv->mce_banks[bank * 4] = ~(uint64_t)0;
8168 }
8169 }
8170 }
8171
x86_cpu_adjust_level(X86CPU * cpu,uint32_t * min,uint32_t value)8172 static void x86_cpu_adjust_level(X86CPU *cpu, uint32_t *min, uint32_t value)
8173 {
8174 if (*min < value) {
8175 *min = value;
8176 }
8177 }
8178
8179 /* Increase cpuid_min_{level,xlevel,xlevel2} automatically, if appropriate */
x86_cpu_adjust_feat_level(X86CPU * cpu,FeatureWord w)8180 static void x86_cpu_adjust_feat_level(X86CPU *cpu, FeatureWord w)
8181 {
8182 CPUX86State *env = &cpu->env;
8183 FeatureWordInfo *fi = &feature_word_info[w];
8184 uint32_t eax = fi->cpuid.eax;
8185 uint32_t region = eax & 0xF0000000;
8186
8187 assert(feature_word_info[w].type == CPUID_FEATURE_WORD);
8188 if (!env->features[w]) {
8189 return;
8190 }
8191
8192 switch (region) {
8193 case 0x00000000:
8194 x86_cpu_adjust_level(cpu, &env->cpuid_min_level, eax);
8195 break;
8196 case 0x80000000:
8197 x86_cpu_adjust_level(cpu, &env->cpuid_min_xlevel, eax);
8198 break;
8199 case 0xC0000000:
8200 x86_cpu_adjust_level(cpu, &env->cpuid_min_xlevel2, eax);
8201 break;
8202 }
8203
8204 if (eax == 7) {
8205 x86_cpu_adjust_level(cpu, &env->cpuid_min_level_func7,
8206 fi->cpuid.ecx);
8207 }
8208 }
8209
8210 /* Calculate XSAVE components based on the configured CPU feature flags */
x86_cpu_enable_xsave_components(X86CPU * cpu)8211 static void x86_cpu_enable_xsave_components(X86CPU *cpu)
8212 {
8213 CPUX86State *env = &cpu->env;
8214 int i;
8215 uint64_t mask;
8216 static bool request_perm;
8217
8218 if (!(env->features[FEAT_1_ECX] & CPUID_EXT_XSAVE)) {
8219 env->features[FEAT_XSAVE_XCR0_LO] = 0;
8220 env->features[FEAT_XSAVE_XCR0_HI] = 0;
8221 env->features[FEAT_XSAVE_XSS_LO] = 0;
8222 env->features[FEAT_XSAVE_XSS_HI] = 0;
8223 return;
8224 }
8225
8226 mask = 0;
8227 for (i = 0; i < ARRAY_SIZE(x86_ext_save_areas); i++) {
8228 const ExtSaveArea *esa = &x86_ext_save_areas[i];
8229 if (cpuid_has_xsave_feature(env, esa)) {
8230 mask |= (1ULL << i);
8231 }
8232 }
8233
8234 /* Only request permission for first vcpu */
8235 if (kvm_enabled() && !request_perm) {
8236 kvm_request_xsave_components(cpu, mask);
8237 request_perm = true;
8238 }
8239
8240 env->features[FEAT_XSAVE_XCR0_LO] = mask & CPUID_XSTATE_XCR0_MASK;
8241 env->features[FEAT_XSAVE_XCR0_HI] = (mask & CPUID_XSTATE_XCR0_MASK) >> 32;
8242 env->features[FEAT_XSAVE_XSS_LO] = mask & CPUID_XSTATE_XSS_MASK;
8243 env->features[FEAT_XSAVE_XSS_HI] = (mask & CPUID_XSTATE_XSS_MASK) >> 32;
8244 }
8245
8246 /***** Steps involved on loading and filtering CPUID data
8247 *
8248 * When initializing and realizing a CPU object, the steps
8249 * involved in setting up CPUID data are:
8250 *
8251 * 1) Loading CPU model definition (X86CPUDefinition). This is
8252 * implemented by x86_cpu_load_model() and should be completely
8253 * transparent, as it is done automatically by instance_init.
8254 * No code should need to look at X86CPUDefinition structs
8255 * outside instance_init.
8256 *
8257 * 2) CPU expansion. This is done by realize before CPUID
8258 * filtering, and will make sure host/accelerator data is
8259 * loaded for CPU models that depend on host capabilities
8260 * (e.g. "host"). Done by x86_cpu_expand_features().
8261 *
8262 * 3) CPUID filtering. This initializes extra data related to
8263 * CPUID, and checks if the host supports all capabilities
8264 * required by the CPU. Runnability of a CPU model is
8265 * determined at this step. Done by x86_cpu_filter_features().
8266 *
8267 * Some operations don't require all steps to be performed.
8268 * More precisely:
8269 *
8270 * - CPU instance creation (instance_init) will run only CPU
8271 * model loading. CPU expansion can't run at instance_init-time
8272 * because host/accelerator data may be not available yet.
8273 * - CPU realization will perform both CPU model expansion and CPUID
8274 * filtering, and return an error in case one of them fails.
8275 * - query-cpu-definitions needs to run all 3 steps. It needs
8276 * to run CPUID filtering, as the 'unavailable-features'
8277 * field is set based on the filtering results.
8278 * - The query-cpu-model-expansion QMP command only needs to run
8279 * CPU model loading and CPU expansion. It should not filter
8280 * any CPUID data based on host capabilities.
8281 */
8282
8283 /* Expand CPU configuration data, based on configured features
8284 * and host/accelerator capabilities when appropriate.
8285 */
x86_cpu_expand_features(X86CPU * cpu,Error ** errp)8286 void x86_cpu_expand_features(X86CPU *cpu, Error **errp)
8287 {
8288 CPUX86State *env = &cpu->env;
8289 FeatureWord w;
8290 int i;
8291 GList *l;
8292
8293 for (l = plus_features; l; l = l->next) {
8294 const char *prop = l->data;
8295 if (!object_property_set_bool(OBJECT(cpu), prop, true, errp)) {
8296 return;
8297 }
8298 }
8299
8300 for (l = minus_features; l; l = l->next) {
8301 const char *prop = l->data;
8302 if (!object_property_set_bool(OBJECT(cpu), prop, false, errp)) {
8303 return;
8304 }
8305 }
8306
8307 /*TODO: Now cpu->max_features doesn't overwrite features
8308 * set using QOM properties, and we can convert
8309 * plus_features & minus_features to global properties
8310 * inside x86_cpu_parse_featurestr() too.
8311 */
8312 if (cpu->max_features) {
8313 for (w = 0; w < FEATURE_WORDS; w++) {
8314 /* Override only features that weren't set explicitly
8315 * by the user.
8316 */
8317 env->features[w] |=
8318 x86_cpu_get_supported_feature_word(cpu, w) &
8319 ~env->user_features[w] &
8320 ~feature_word_info[w].no_autoenable_flags;
8321 }
8322
8323 if ((env->features[FEAT_7_1_EDX] & CPUID_7_1_EDX_AVX10) && !env->avx10_version) {
8324 uint32_t eax, ebx, ecx, edx;
8325 x86_cpu_get_supported_cpuid(0x24, 0, &eax, &ebx, &ecx, &edx);
8326 env->avx10_version = ebx & 0xff;
8327 }
8328 }
8329
8330 if (x86_threads_per_pkg(&env->topo_info) > 1) {
8331 env->features[FEAT_1_EDX] |= CPUID_HT;
8332
8333 /*
8334 * The Linux kernel checks for the CMPLegacy bit and
8335 * discards multiple thread information if it is set.
8336 * So don't set it here for Intel (and other processors
8337 * following Intel's behavior) to make Linux guests happy.
8338 */
8339 if (!IS_INTEL_CPU(env) && !IS_ZHAOXIN_CPU(env)) {
8340 env->features[FEAT_8000_0001_ECX] |= CPUID_EXT3_CMP_LEG;
8341 }
8342 }
8343
8344 for (i = 0; i < ARRAY_SIZE(feature_dependencies); i++) {
8345 FeatureDep *d = &feature_dependencies[i];
8346 if (!(env->features[d->from.index] & d->from.mask)) {
8347 uint64_t unavailable_features = env->features[d->to.index] & d->to.mask;
8348
8349 /* Not an error unless the dependent feature was added explicitly. */
8350 mark_unavailable_features(cpu, d->to.index,
8351 unavailable_features & env->user_features[d->to.index],
8352 "This feature depends on other features that were not requested");
8353
8354 env->features[d->to.index] &= ~unavailable_features;
8355 }
8356 }
8357
8358 if (!kvm_enabled() || !cpu->expose_kvm) {
8359 env->features[FEAT_KVM] = 0;
8360 }
8361
8362 x86_cpu_enable_xsave_components(cpu);
8363
8364 /* CPUID[EAX=7,ECX=0].EBX always increased level automatically: */
8365 x86_cpu_adjust_feat_level(cpu, FEAT_7_0_EBX);
8366 if (cpu->full_cpuid_auto_level) {
8367 x86_cpu_adjust_feat_level(cpu, FEAT_1_EDX);
8368 x86_cpu_adjust_feat_level(cpu, FEAT_1_ECX);
8369 x86_cpu_adjust_feat_level(cpu, FEAT_6_EAX);
8370 x86_cpu_adjust_feat_level(cpu, FEAT_7_0_ECX);
8371 x86_cpu_adjust_feat_level(cpu, FEAT_7_1_EAX);
8372 x86_cpu_adjust_feat_level(cpu, FEAT_7_1_ECX);
8373 x86_cpu_adjust_feat_level(cpu, FEAT_7_1_EDX);
8374 x86_cpu_adjust_feat_level(cpu, FEAT_7_2_EDX);
8375 x86_cpu_adjust_feat_level(cpu, FEAT_8000_0001_EDX);
8376 x86_cpu_adjust_feat_level(cpu, FEAT_8000_0001_ECX);
8377 x86_cpu_adjust_feat_level(cpu, FEAT_8000_0007_EDX);
8378 x86_cpu_adjust_feat_level(cpu, FEAT_8000_0008_EBX);
8379 x86_cpu_adjust_feat_level(cpu, FEAT_C000_0001_EDX);
8380 x86_cpu_adjust_feat_level(cpu, FEAT_SVM);
8381 x86_cpu_adjust_feat_level(cpu, FEAT_XSAVE);
8382
8383 /* Intel Processor Trace requires CPUID[0x14] */
8384 if ((env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_INTEL_PT)) {
8385 if (cpu->intel_pt_auto_level) {
8386 x86_cpu_adjust_level(cpu, &cpu->env.cpuid_min_level, 0x14);
8387 } else if (cpu->env.cpuid_min_level < 0x14) {
8388 mark_unavailable_features(cpu, FEAT_7_0_EBX,
8389 CPUID_7_0_EBX_INTEL_PT,
8390 "Intel PT need CPUID leaf 0x14, please set by \"-cpu ...,intel-pt=on,min-level=0x14\"");
8391 }
8392 }
8393
8394 /*
8395 * Intel CPU topology with multi-dies support requires CPUID[0x1F].
8396 * For AMD Rome/Milan, cpuid level is 0x10, and guest OS should detect
8397 * extended toplogy by leaf 0xB. Only adjust it for Intel CPU, unless
8398 * cpu->vendor_cpuid_only has been unset for compatibility with older
8399 * machine types.
8400 */
8401 if (x86_has_cpuid_0x1f(cpu) &&
8402 (IS_INTEL_CPU(env) || !cpu->vendor_cpuid_only)) {
8403 x86_cpu_adjust_level(cpu, &env->cpuid_min_level, 0x1F);
8404 }
8405
8406 /* Advanced Vector Extensions 10 (AVX10) requires CPUID[0x24] */
8407 if (env->features[FEAT_7_1_EDX] & CPUID_7_1_EDX_AVX10) {
8408 x86_cpu_adjust_level(cpu, &env->cpuid_min_level, 0x24);
8409 }
8410
8411 /* SVM requires CPUID[0x8000000A] */
8412 if (env->features[FEAT_8000_0001_ECX] & CPUID_EXT3_SVM) {
8413 x86_cpu_adjust_level(cpu, &env->cpuid_min_xlevel, 0x8000000A);
8414 }
8415
8416 /* SEV requires CPUID[0x8000001F] */
8417 if (sev_enabled()) {
8418 x86_cpu_adjust_level(cpu, &env->cpuid_min_xlevel, 0x8000001F);
8419 }
8420
8421 if (env->features[FEAT_8000_0021_EAX]) {
8422 x86_cpu_adjust_level(cpu, &env->cpuid_min_xlevel, 0x80000021);
8423 }
8424
8425 /* SGX requires CPUID[0x12] for EPC enumeration */
8426 if (env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_SGX) {
8427 x86_cpu_adjust_level(cpu, &env->cpuid_min_level, 0x12);
8428 }
8429 }
8430
8431 /* Set cpuid_*level* based on cpuid_min_*level, if not explicitly set */
8432 if (env->cpuid_level_func7 == UINT32_MAX) {
8433 env->cpuid_level_func7 = env->cpuid_min_level_func7;
8434 }
8435 if (env->cpuid_level == UINT32_MAX) {
8436 env->cpuid_level = env->cpuid_min_level;
8437 }
8438 if (env->cpuid_xlevel == UINT32_MAX) {
8439 env->cpuid_xlevel = env->cpuid_min_xlevel;
8440 }
8441 if (env->cpuid_xlevel2 == UINT32_MAX) {
8442 env->cpuid_xlevel2 = env->cpuid_min_xlevel2;
8443 }
8444
8445 if (kvm_enabled() && !kvm_hyperv_expand_features(cpu, errp)) {
8446 return;
8447 }
8448 }
8449
8450 /*
8451 * Finishes initialization of CPUID data, filters CPU feature
8452 * words based on host availability of each feature.
8453 *
8454 * Returns: true if any flag is not supported by the host, false otherwise.
8455 */
x86_cpu_filter_features(X86CPU * cpu,bool verbose)8456 static bool x86_cpu_filter_features(X86CPU *cpu, bool verbose)
8457 {
8458 CPUX86State *env = &cpu->env;
8459 FeatureWord w;
8460 const char *prefix = NULL;
8461 bool have_filtered_features;
8462
8463 uint32_t eax_0, ebx_0, ecx_0, edx_0;
8464 uint32_t eax_1, ebx_1, ecx_1, edx_1;
8465
8466 if (verbose) {
8467 prefix = accel_uses_host_cpuid()
8468 ? "host doesn't support requested feature"
8469 : "TCG doesn't support requested feature";
8470 }
8471
8472 for (w = 0; w < FEATURE_WORDS; w++) {
8473 uint64_t host_feat =
8474 x86_cpu_get_supported_feature_word(NULL, w);
8475 uint64_t requested_features = env->features[w];
8476 uint64_t unavailable_features = requested_features & ~host_feat;
8477 mark_unavailable_features(cpu, w, unavailable_features, prefix);
8478 }
8479
8480 /*
8481 * Check that KVM actually allows the processor tracing features that
8482 * are advertised by cpu_x86_cpuid(). Keep these two in sync.
8483 */
8484 if ((env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_INTEL_PT) &&
8485 kvm_enabled()) {
8486 x86_cpu_get_supported_cpuid(0x14, 0,
8487 &eax_0, &ebx_0, &ecx_0, &edx_0);
8488 x86_cpu_get_supported_cpuid(0x14, 1,
8489 &eax_1, &ebx_1, &ecx_1, &edx_1);
8490
8491 if (!eax_0 ||
8492 ((ebx_0 & INTEL_PT_MINIMAL_EBX) != INTEL_PT_MINIMAL_EBX) ||
8493 ((ecx_0 & INTEL_PT_MINIMAL_ECX) != INTEL_PT_MINIMAL_ECX) ||
8494 ((eax_1 & INTEL_PT_MTC_BITMAP) != INTEL_PT_MTC_BITMAP) ||
8495 ((eax_1 & INTEL_PT_ADDR_RANGES_NUM_MASK) <
8496 INTEL_PT_ADDR_RANGES_NUM) ||
8497 ((ebx_1 & (INTEL_PT_PSB_BITMAP | INTEL_PT_CYCLE_BITMAP)) !=
8498 (INTEL_PT_PSB_BITMAP | INTEL_PT_CYCLE_BITMAP)) ||
8499 ((ecx_0 & CPUID_14_0_ECX_LIP) !=
8500 (env->features[FEAT_14_0_ECX] & CPUID_14_0_ECX_LIP))) {
8501 /*
8502 * Processor Trace capabilities aren't configurable, so if the
8503 * host can't emulate the capabilities we report on
8504 * cpu_x86_cpuid(), intel-pt can't be enabled on the current host.
8505 */
8506 mark_unavailable_features(cpu, FEAT_7_0_EBX, CPUID_7_0_EBX_INTEL_PT, prefix);
8507 }
8508 }
8509
8510 have_filtered_features = x86_cpu_have_filtered_features(cpu);
8511
8512 if (env->features[FEAT_7_1_EDX] & CPUID_7_1_EDX_AVX10) {
8513 x86_cpu_get_supported_cpuid(0x24, 0,
8514 &eax_0, &ebx_0, &ecx_0, &edx_0);
8515 uint8_t version = ebx_0 & 0xff;
8516
8517 if (version < env->avx10_version) {
8518 if (prefix) {
8519 warn_report("%s: avx10.%d. Adjust to avx10.%d",
8520 prefix, env->avx10_version, version);
8521 }
8522 env->avx10_version = version;
8523 have_filtered_features = true;
8524 }
8525 } else if (env->avx10_version) {
8526 if (prefix) {
8527 warn_report("%s: avx10.%d.", prefix, env->avx10_version);
8528 }
8529 have_filtered_features = true;
8530 }
8531
8532 return have_filtered_features;
8533 }
8534
x86_cpu_hyperv_realize(X86CPU * cpu)8535 static void x86_cpu_hyperv_realize(X86CPU *cpu)
8536 {
8537 size_t len;
8538
8539 /* Hyper-V vendor id */
8540 if (!cpu->hyperv_vendor) {
8541 object_property_set_str(OBJECT(cpu), "hv-vendor-id", "Microsoft Hv",
8542 &error_abort);
8543 }
8544 len = strlen(cpu->hyperv_vendor);
8545 if (len > 12) {
8546 warn_report("hv-vendor-id truncated to 12 characters");
8547 len = 12;
8548 }
8549 memset(cpu->hyperv_vendor_id, 0, 12);
8550 memcpy(cpu->hyperv_vendor_id, cpu->hyperv_vendor, len);
8551
8552 /* 'Hv#1' interface identification*/
8553 cpu->hyperv_interface_id[0] = 0x31237648;
8554 cpu->hyperv_interface_id[1] = 0;
8555 cpu->hyperv_interface_id[2] = 0;
8556 cpu->hyperv_interface_id[3] = 0;
8557
8558 /* Hypervisor implementation limits */
8559 cpu->hyperv_limits[0] = 64;
8560 cpu->hyperv_limits[1] = 0;
8561 cpu->hyperv_limits[2] = 0;
8562 }
8563
8564 #ifndef CONFIG_USER_ONLY
x86_cpu_update_smp_cache_topo(MachineState * ms,X86CPU * cpu,Error ** errp)8565 static bool x86_cpu_update_smp_cache_topo(MachineState *ms, X86CPU *cpu,
8566 Error **errp)
8567 {
8568 CPUX86State *env = &cpu->env;
8569 CpuTopologyLevel level;
8570
8571 level = machine_get_cache_topo_level(ms, CACHE_LEVEL_AND_TYPE_L1D);
8572 if (level != CPU_TOPOLOGY_LEVEL_DEFAULT) {
8573 env->cache_info_cpuid4.l1d_cache->share_level = level;
8574 env->cache_info_amd.l1d_cache->share_level = level;
8575 } else {
8576 machine_set_cache_topo_level(ms, CACHE_LEVEL_AND_TYPE_L1D,
8577 env->cache_info_cpuid4.l1d_cache->share_level);
8578 machine_set_cache_topo_level(ms, CACHE_LEVEL_AND_TYPE_L1D,
8579 env->cache_info_amd.l1d_cache->share_level);
8580 }
8581
8582 level = machine_get_cache_topo_level(ms, CACHE_LEVEL_AND_TYPE_L1I);
8583 if (level != CPU_TOPOLOGY_LEVEL_DEFAULT) {
8584 env->cache_info_cpuid4.l1i_cache->share_level = level;
8585 env->cache_info_amd.l1i_cache->share_level = level;
8586 } else {
8587 machine_set_cache_topo_level(ms, CACHE_LEVEL_AND_TYPE_L1I,
8588 env->cache_info_cpuid4.l1i_cache->share_level);
8589 machine_set_cache_topo_level(ms, CACHE_LEVEL_AND_TYPE_L1I,
8590 env->cache_info_amd.l1i_cache->share_level);
8591 }
8592
8593 level = machine_get_cache_topo_level(ms, CACHE_LEVEL_AND_TYPE_L2);
8594 if (level != CPU_TOPOLOGY_LEVEL_DEFAULT) {
8595 env->cache_info_cpuid4.l2_cache->share_level = level;
8596 env->cache_info_amd.l2_cache->share_level = level;
8597 } else {
8598 machine_set_cache_topo_level(ms, CACHE_LEVEL_AND_TYPE_L2,
8599 env->cache_info_cpuid4.l2_cache->share_level);
8600 machine_set_cache_topo_level(ms, CACHE_LEVEL_AND_TYPE_L2,
8601 env->cache_info_amd.l2_cache->share_level);
8602 }
8603
8604 level = machine_get_cache_topo_level(ms, CACHE_LEVEL_AND_TYPE_L3);
8605 if (level != CPU_TOPOLOGY_LEVEL_DEFAULT) {
8606 env->cache_info_cpuid4.l3_cache->share_level = level;
8607 env->cache_info_amd.l3_cache->share_level = level;
8608 } else {
8609 machine_set_cache_topo_level(ms, CACHE_LEVEL_AND_TYPE_L3,
8610 env->cache_info_cpuid4.l3_cache->share_level);
8611 machine_set_cache_topo_level(ms, CACHE_LEVEL_AND_TYPE_L3,
8612 env->cache_info_amd.l3_cache->share_level);
8613 }
8614
8615 if (!machine_check_smp_cache(ms, errp)) {
8616 return false;
8617 }
8618 return true;
8619 }
8620 #endif
8621
x86_cpu_realizefn(DeviceState * dev,Error ** errp)8622 static void x86_cpu_realizefn(DeviceState *dev, Error **errp)
8623 {
8624 CPUState *cs = CPU(dev);
8625 X86CPU *cpu = X86_CPU(dev);
8626 X86CPUClass *xcc = X86_CPU_GET_CLASS(dev);
8627 CPUX86State *env = &cpu->env;
8628 Error *local_err = NULL;
8629 unsigned requested_lbr_fmt;
8630
8631 #if defined(CONFIG_TCG) && !defined(CONFIG_USER_ONLY)
8632 /* Use pc-relative instructions in system-mode */
8633 tcg_cflags_set(cs, CF_PCREL);
8634 #endif
8635
8636 if (cpu->apic_id == UNASSIGNED_APIC_ID) {
8637 error_setg(errp, "apic-id property was not initialized properly");
8638 return;
8639 }
8640
8641 /*
8642 * Process Hyper-V enlightenments.
8643 * Note: this currently has to happen before the expansion of CPU features.
8644 */
8645 x86_cpu_hyperv_realize(cpu);
8646
8647 x86_cpu_expand_features(cpu, &local_err);
8648 if (local_err) {
8649 goto out;
8650 }
8651
8652 /*
8653 * Override env->features[FEAT_PERF_CAPABILITIES].LBR_FMT
8654 * with user-provided setting.
8655 */
8656 if (cpu->lbr_fmt != ~PERF_CAP_LBR_FMT) {
8657 if ((cpu->lbr_fmt & PERF_CAP_LBR_FMT) != cpu->lbr_fmt) {
8658 error_setg(errp, "invalid lbr-fmt");
8659 return;
8660 }
8661 env->features[FEAT_PERF_CAPABILITIES] &= ~PERF_CAP_LBR_FMT;
8662 env->features[FEAT_PERF_CAPABILITIES] |= cpu->lbr_fmt;
8663 }
8664
8665 /*
8666 * vPMU LBR is supported when 1) KVM is enabled 2) Option pmu=on and
8667 * 3)vPMU LBR format matches that of host setting.
8668 */
8669 requested_lbr_fmt =
8670 env->features[FEAT_PERF_CAPABILITIES] & PERF_CAP_LBR_FMT;
8671 if (requested_lbr_fmt && kvm_enabled()) {
8672 uint64_t host_perf_cap =
8673 x86_cpu_get_supported_feature_word(NULL, FEAT_PERF_CAPABILITIES);
8674 unsigned host_lbr_fmt = host_perf_cap & PERF_CAP_LBR_FMT;
8675
8676 if (!cpu->enable_pmu) {
8677 error_setg(errp, "vPMU: LBR is unsupported without pmu=on");
8678 return;
8679 }
8680 if (requested_lbr_fmt != host_lbr_fmt) {
8681 error_setg(errp, "vPMU: the lbr-fmt value (0x%x) does not match "
8682 "the host value (0x%x).",
8683 requested_lbr_fmt, host_lbr_fmt);
8684 return;
8685 }
8686 }
8687
8688 if (x86_cpu_filter_features(cpu, cpu->check_cpuid || cpu->enforce_cpuid)) {
8689 if (cpu->enforce_cpuid) {
8690 error_setg(&local_err,
8691 accel_uses_host_cpuid() ?
8692 "Host doesn't support requested features" :
8693 "TCG doesn't support requested features");
8694 goto out;
8695 }
8696 }
8697
8698 /* On AMD CPUs, some CPUID[8000_0001].EDX bits must match the bits on
8699 * CPUID[1].EDX.
8700 */
8701 if (IS_AMD_CPU(env)) {
8702 env->features[FEAT_8000_0001_EDX] &= ~CPUID_EXT2_AMD_ALIASES;
8703 env->features[FEAT_8000_0001_EDX] |= (env->features[FEAT_1_EDX]
8704 & CPUID_EXT2_AMD_ALIASES);
8705 }
8706
8707 x86_cpu_set_sgxlepubkeyhash(env);
8708
8709 /*
8710 * note: the call to the framework needs to happen after feature expansion,
8711 * but before the checks/modifications to ucode_rev, mwait, phys_bits.
8712 * These may be set by the accel-specific code,
8713 * and the results are subsequently checked / assumed in this function.
8714 */
8715 cpu_exec_realizefn(cs, &local_err);
8716 if (local_err != NULL) {
8717 error_propagate(errp, local_err);
8718 return;
8719 }
8720
8721 if (xcc->host_cpuid_required && !accel_uses_host_cpuid()) {
8722 g_autofree char *name = x86_cpu_class_get_model_name(xcc);
8723 error_setg(&local_err, "CPU model '%s' requires KVM or HVF", name);
8724 goto out;
8725 }
8726
8727 if (cpu->guest_phys_bits == -1) {
8728 /*
8729 * If it was not set by the user, or by the accelerator via
8730 * cpu_exec_realizefn, clear.
8731 */
8732 cpu->guest_phys_bits = 0;
8733 }
8734
8735 if (cpu->ucode_rev == 0) {
8736 /*
8737 * The default is the same as KVM's. Note that this check
8738 * needs to happen after the evenual setting of ucode_rev in
8739 * accel-specific code in cpu_exec_realizefn.
8740 */
8741 if (IS_AMD_CPU(env)) {
8742 cpu->ucode_rev = 0x01000065;
8743 } else {
8744 cpu->ucode_rev = 0x100000000ULL;
8745 }
8746 }
8747
8748 /*
8749 * mwait extended info: needed for Core compatibility
8750 * We always wake on interrupt even if host does not have the capability.
8751 *
8752 * requires the accel-specific code in cpu_exec_realizefn to
8753 * have already acquired the CPUID data into cpu->mwait.
8754 */
8755 cpu->mwait.ecx |= CPUID_MWAIT_EMX | CPUID_MWAIT_IBE;
8756
8757 /*
8758 * Most Intel and certain AMD CPUs support hyperthreading. Even though QEMU
8759 * fixes this issue by adjusting CPUID_0000_0001_EBX and CPUID_8000_0008_ECX
8760 * based on inputs (sockets,cores,threads), it is still better to give
8761 * users a warning.
8762 */
8763 if (IS_AMD_CPU(env) &&
8764 !(env->features[FEAT_8000_0001_ECX] & CPUID_EXT3_TOPOEXT) &&
8765 env->topo_info.threads_per_core > 1) {
8766 warn_report_once("This family of AMD CPU doesn't support "
8767 "hyperthreading(%d). Please configure -smp "
8768 "options properly or try enabling topoext "
8769 "feature.", env->topo_info.threads_per_core);
8770 }
8771
8772 /* For 64bit systems think about the number of physical bits to present.
8773 * ideally this should be the same as the host; anything other than matching
8774 * the host can cause incorrect guest behaviour.
8775 * QEMU used to pick the magic value of 40 bits that corresponds to
8776 * consumer AMD devices but nothing else.
8777 *
8778 * Note that this code assumes features expansion has already been done
8779 * (as it checks for CPUID_EXT2_LM), and also assumes that potential
8780 * phys_bits adjustments to match the host have been already done in
8781 * accel-specific code in cpu_exec_realizefn.
8782 */
8783 if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_LM) {
8784 if (cpu->phys_bits &&
8785 (cpu->phys_bits > TARGET_PHYS_ADDR_SPACE_BITS ||
8786 cpu->phys_bits < 32)) {
8787 error_setg(errp, "phys-bits should be between 32 and %u "
8788 " (but is %u)",
8789 TARGET_PHYS_ADDR_SPACE_BITS, cpu->phys_bits);
8790 return;
8791 }
8792 /*
8793 * 0 means it was not explicitly set by the user (or by machine
8794 * compat_props or by the host code in host-cpu.c).
8795 * In this case, the default is the value used by TCG (40).
8796 */
8797 if (cpu->phys_bits == 0) {
8798 cpu->phys_bits = TCG_PHYS_ADDR_BITS;
8799 }
8800 if (cpu->guest_phys_bits &&
8801 (cpu->guest_phys_bits > cpu->phys_bits ||
8802 cpu->guest_phys_bits < 32)) {
8803 error_setg(errp, "guest-phys-bits should be between 32 and %u "
8804 " (but is %u)",
8805 cpu->phys_bits, cpu->guest_phys_bits);
8806 return;
8807 }
8808 } else {
8809 /* For 32 bit systems don't use the user set value, but keep
8810 * phys_bits consistent with what we tell the guest.
8811 */
8812 if (cpu->phys_bits != 0) {
8813 error_setg(errp, "phys-bits is not user-configurable in 32 bit");
8814 return;
8815 }
8816 if (cpu->guest_phys_bits != 0) {
8817 error_setg(errp, "guest-phys-bits is not user-configurable in 32 bit");
8818 return;
8819 }
8820
8821 if (env->features[FEAT_1_EDX] & (CPUID_PSE36 | CPUID_PAE)) {
8822 cpu->phys_bits = 36;
8823 } else {
8824 cpu->phys_bits = 32;
8825 }
8826 }
8827
8828 /* Cache information initialization */
8829 if (!cpu->legacy_cache) {
8830 const CPUCaches *cache_info =
8831 x86_cpu_get_versioned_cache_info(cpu, xcc->model);
8832
8833 if (!xcc->model || !cache_info) {
8834 g_autofree char *name = x86_cpu_class_get_model_name(xcc);
8835 error_setg(errp,
8836 "CPU model '%s' doesn't support legacy-cache=off", name);
8837 return;
8838 }
8839 env->cache_info_cpuid2 = env->cache_info_cpuid4 = env->cache_info_amd =
8840 *cache_info;
8841 } else {
8842 /* Build legacy cache information */
8843 env->cache_info_cpuid2.l1d_cache = &legacy_l1d_cache;
8844 env->cache_info_cpuid2.l1i_cache = &legacy_l1i_cache;
8845 env->cache_info_cpuid2.l2_cache = &legacy_l2_cache_cpuid2;
8846 env->cache_info_cpuid2.l3_cache = &legacy_l3_cache;
8847
8848 env->cache_info_cpuid4.l1d_cache = &legacy_l1d_cache;
8849 env->cache_info_cpuid4.l1i_cache = &legacy_l1i_cache;
8850 env->cache_info_cpuid4.l2_cache = &legacy_l2_cache;
8851 env->cache_info_cpuid4.l3_cache = &legacy_l3_cache;
8852
8853 env->cache_info_amd.l1d_cache = &legacy_l1d_cache_amd;
8854 env->cache_info_amd.l1i_cache = &legacy_l1i_cache_amd;
8855 env->cache_info_amd.l2_cache = &legacy_l2_cache_amd;
8856 env->cache_info_amd.l3_cache = &legacy_l3_cache;
8857 }
8858
8859 #ifndef CONFIG_USER_ONLY
8860 MachineState *ms = MACHINE(qdev_get_machine());
8861 MachineClass *mc = MACHINE_GET_CLASS(ms);
8862
8863 if (mc->smp_props.has_caches) {
8864 if (!x86_cpu_update_smp_cache_topo(ms, cpu, errp)) {
8865 return;
8866 }
8867 }
8868
8869 qemu_register_reset(x86_cpu_machine_reset_cb, cpu);
8870
8871 if (cpu->env.features[FEAT_1_EDX] & CPUID_APIC || ms->smp.cpus > 1) {
8872 x86_cpu_apic_create(cpu, &local_err);
8873 if (local_err != NULL) {
8874 goto out;
8875 }
8876 }
8877 #endif
8878
8879 mce_init(cpu);
8880
8881 x86_cpu_gdb_init(cs);
8882 qemu_init_vcpu(cs);
8883
8884 #ifndef CONFIG_USER_ONLY
8885 x86_cpu_apic_realize(cpu, &local_err);
8886 if (local_err != NULL) {
8887 goto out;
8888 }
8889 #endif /* !CONFIG_USER_ONLY */
8890 cpu_reset(cs);
8891
8892 xcc->parent_realize(dev, &local_err);
8893
8894 out:
8895 if (local_err != NULL) {
8896 error_propagate(errp, local_err);
8897 return;
8898 }
8899 }
8900
x86_cpu_unrealizefn(DeviceState * dev)8901 static void x86_cpu_unrealizefn(DeviceState *dev)
8902 {
8903 X86CPU *cpu = X86_CPU(dev);
8904 X86CPUClass *xcc = X86_CPU_GET_CLASS(dev);
8905
8906 #ifndef CONFIG_USER_ONLY
8907 cpu_remove_sync(CPU(dev));
8908 qemu_unregister_reset(x86_cpu_machine_reset_cb, dev);
8909 #endif
8910
8911 if (cpu->apic_state) {
8912 object_unparent(OBJECT(cpu->apic_state));
8913 cpu->apic_state = NULL;
8914 }
8915
8916 xcc->parent_unrealize(dev);
8917 }
8918
8919 typedef struct BitProperty {
8920 FeatureWord w;
8921 uint64_t mask;
8922 } BitProperty;
8923
x86_cpu_get_bit_prop(Object * obj,Visitor * v,const char * name,void * opaque,Error ** errp)8924 static void x86_cpu_get_bit_prop(Object *obj, Visitor *v, const char *name,
8925 void *opaque, Error **errp)
8926 {
8927 X86CPU *cpu = X86_CPU(obj);
8928 BitProperty *fp = opaque;
8929 uint64_t f = cpu->env.features[fp->w];
8930 bool value = (f & fp->mask) == fp->mask;
8931 visit_type_bool(v, name, &value, errp);
8932 }
8933
x86_cpu_set_bit_prop(Object * obj,Visitor * v,const char * name,void * opaque,Error ** errp)8934 static void x86_cpu_set_bit_prop(Object *obj, Visitor *v, const char *name,
8935 void *opaque, Error **errp)
8936 {
8937 DeviceState *dev = DEVICE(obj);
8938 X86CPU *cpu = X86_CPU(obj);
8939 BitProperty *fp = opaque;
8940 bool value;
8941
8942 if (dev->realized) {
8943 qdev_prop_set_after_realize(dev, name, errp);
8944 return;
8945 }
8946
8947 if (!visit_type_bool(v, name, &value, errp)) {
8948 return;
8949 }
8950
8951 if (value) {
8952 cpu->env.features[fp->w] |= fp->mask;
8953 } else {
8954 cpu->env.features[fp->w] &= ~fp->mask;
8955 }
8956 cpu->env.user_features[fp->w] |= fp->mask;
8957 }
8958
8959 /* Register a boolean property to get/set a single bit in a uint32_t field.
8960 *
8961 * The same property name can be registered multiple times to make it affect
8962 * multiple bits in the same FeatureWord. In that case, the getter will return
8963 * true only if all bits are set.
8964 */
x86_cpu_register_bit_prop(X86CPUClass * xcc,const char * prop_name,FeatureWord w,int bitnr)8965 static void x86_cpu_register_bit_prop(X86CPUClass *xcc,
8966 const char *prop_name,
8967 FeatureWord w,
8968 int bitnr)
8969 {
8970 ObjectClass *oc = OBJECT_CLASS(xcc);
8971 BitProperty *fp;
8972 ObjectProperty *op;
8973 uint64_t mask = (1ULL << bitnr);
8974
8975 op = object_class_property_find(oc, prop_name);
8976 if (op) {
8977 fp = op->opaque;
8978 assert(fp->w == w);
8979 fp->mask |= mask;
8980 } else {
8981 fp = g_new0(BitProperty, 1);
8982 fp->w = w;
8983 fp->mask = mask;
8984 object_class_property_add(oc, prop_name, "bool",
8985 x86_cpu_get_bit_prop,
8986 x86_cpu_set_bit_prop,
8987 NULL, fp);
8988 }
8989 }
8990
x86_cpu_register_feature_bit_props(X86CPUClass * xcc,FeatureWord w,int bitnr)8991 static void x86_cpu_register_feature_bit_props(X86CPUClass *xcc,
8992 FeatureWord w,
8993 int bitnr)
8994 {
8995 FeatureWordInfo *fi = &feature_word_info[w];
8996 const char *name = fi->feat_names[bitnr];
8997
8998 if (!name) {
8999 return;
9000 }
9001
9002 /* Property names should use "-" instead of "_".
9003 * Old names containing underscores are registered as aliases
9004 * using object_property_add_alias()
9005 */
9006 assert(!strchr(name, '_'));
9007 /* aliases don't use "|" delimiters anymore, they are registered
9008 * manually using object_property_add_alias() */
9009 assert(!strchr(name, '|'));
9010 x86_cpu_register_bit_prop(xcc, name, w, bitnr);
9011 }
9012
x86_cpu_post_initfn(Object * obj)9013 static void x86_cpu_post_initfn(Object *obj)
9014 {
9015 static bool first = true;
9016 uint64_t supported_xcr0;
9017 int i;
9018
9019 if (first) {
9020 first = false;
9021
9022 supported_xcr0 =
9023 ((uint64_t) x86_cpu_get_supported_feature_word(NULL, FEAT_XSAVE_XCR0_HI) << 32) |
9024 x86_cpu_get_supported_feature_word(NULL, FEAT_XSAVE_XCR0_LO);
9025
9026 for (i = XSTATE_SSE_BIT + 1; i < XSAVE_STATE_AREA_COUNT; i++) {
9027 ExtSaveArea *esa = &x86_ext_save_areas[i];
9028
9029 if (!(supported_xcr0 & (1 << i))) {
9030 esa->size = 0;
9031 }
9032 }
9033 }
9034
9035 accel_cpu_instance_init(CPU(obj));
9036
9037 #ifndef CONFIG_USER_ONLY
9038 if (current_machine && current_machine->cgs) {
9039 x86_confidential_guest_cpu_instance_init(
9040 X86_CONFIDENTIAL_GUEST(current_machine->cgs), (CPU(obj)));
9041 }
9042 #endif
9043 }
9044
x86_cpu_init_default_topo(X86CPU * cpu)9045 static void x86_cpu_init_default_topo(X86CPU *cpu)
9046 {
9047 CPUX86State *env = &cpu->env;
9048
9049 env->topo_info = (X86CPUTopoInfo) {1, 1, 1, 1};
9050
9051 /* thread, core and socket levels are set by default. */
9052 set_bit(CPU_TOPOLOGY_LEVEL_THREAD, env->avail_cpu_topo);
9053 set_bit(CPU_TOPOLOGY_LEVEL_CORE, env->avail_cpu_topo);
9054 set_bit(CPU_TOPOLOGY_LEVEL_SOCKET, env->avail_cpu_topo);
9055 }
9056
x86_cpu_initfn(Object * obj)9057 static void x86_cpu_initfn(Object *obj)
9058 {
9059 X86CPU *cpu = X86_CPU(obj);
9060 X86CPUClass *xcc = X86_CPU_GET_CLASS(obj);
9061 CPUX86State *env = &cpu->env;
9062
9063 x86_cpu_init_default_topo(cpu);
9064
9065 object_property_add(obj, "feature-words", "X86CPUFeatureWordInfo",
9066 x86_cpu_get_feature_words,
9067 NULL, NULL, (void *)env->features);
9068 object_property_add(obj, "filtered-features", "X86CPUFeatureWordInfo",
9069 x86_cpu_get_feature_words,
9070 NULL, NULL, (void *)cpu->filtered_features);
9071
9072 object_property_add_alias(obj, "sse3", obj, "pni");
9073 object_property_add_alias(obj, "pclmuldq", obj, "pclmulqdq");
9074 object_property_add_alias(obj, "sse4-1", obj, "sse4.1");
9075 object_property_add_alias(obj, "sse4-2", obj, "sse4.2");
9076 object_property_add_alias(obj, "xd", obj, "nx");
9077 object_property_add_alias(obj, "ffxsr", obj, "fxsr-opt");
9078 object_property_add_alias(obj, "i64", obj, "lm");
9079
9080 object_property_add_alias(obj, "ds_cpl", obj, "ds-cpl");
9081 object_property_add_alias(obj, "tsc_adjust", obj, "tsc-adjust");
9082 object_property_add_alias(obj, "fxsr_opt", obj, "fxsr-opt");
9083 object_property_add_alias(obj, "lahf_lm", obj, "lahf-lm");
9084 object_property_add_alias(obj, "cmp_legacy", obj, "cmp-legacy");
9085 object_property_add_alias(obj, "nodeid_msr", obj, "nodeid-msr");
9086 object_property_add_alias(obj, "perfctr_core", obj, "perfctr-core");
9087 object_property_add_alias(obj, "perfctr_nb", obj, "perfctr-nb");
9088 object_property_add_alias(obj, "kvm_nopiodelay", obj, "kvm-nopiodelay");
9089 object_property_add_alias(obj, "kvm_mmu", obj, "kvm-mmu");
9090 object_property_add_alias(obj, "kvm_asyncpf", obj, "kvm-asyncpf");
9091 object_property_add_alias(obj, "kvm_asyncpf_int", obj, "kvm-asyncpf-int");
9092 object_property_add_alias(obj, "kvm_steal_time", obj, "kvm-steal-time");
9093 object_property_add_alias(obj, "kvm_pv_eoi", obj, "kvm-pv-eoi");
9094 object_property_add_alias(obj, "kvm_pv_unhalt", obj, "kvm-pv-unhalt");
9095 object_property_add_alias(obj, "kvm_poll_control", obj, "kvm-poll-control");
9096 object_property_add_alias(obj, "svm_lock", obj, "svm-lock");
9097 object_property_add_alias(obj, "nrip_save", obj, "nrip-save");
9098 object_property_add_alias(obj, "tsc_scale", obj, "tsc-scale");
9099 object_property_add_alias(obj, "vmcb_clean", obj, "vmcb-clean");
9100 object_property_add_alias(obj, "pause_filter", obj, "pause-filter");
9101 object_property_add_alias(obj, "sse4_1", obj, "sse4.1");
9102 object_property_add_alias(obj, "sse4_2", obj, "sse4.2");
9103
9104 object_property_add_alias(obj, "hv-apicv", obj, "hv-avic");
9105 cpu->lbr_fmt = ~PERF_CAP_LBR_FMT;
9106 object_property_add_alias(obj, "lbr_fmt", obj, "lbr-fmt");
9107
9108 if (xcc->model) {
9109 x86_cpu_load_model(cpu, xcc->model);
9110 }
9111 }
9112
x86_cpu_get_arch_id(CPUState * cs)9113 static int64_t x86_cpu_get_arch_id(CPUState *cs)
9114 {
9115 X86CPU *cpu = X86_CPU(cs);
9116
9117 return cpu->apic_id;
9118 }
9119
9120 #if !defined(CONFIG_USER_ONLY)
x86_cpu_get_paging_enabled(const CPUState * cs)9121 static bool x86_cpu_get_paging_enabled(const CPUState *cs)
9122 {
9123 X86CPU *cpu = X86_CPU(cs);
9124
9125 return cpu->env.cr[0] & CR0_PG_MASK;
9126 }
9127 #endif /* !CONFIG_USER_ONLY */
9128
x86_cpu_set_pc(CPUState * cs,vaddr value)9129 static void x86_cpu_set_pc(CPUState *cs, vaddr value)
9130 {
9131 X86CPU *cpu = X86_CPU(cs);
9132
9133 cpu->env.eip = value;
9134 }
9135
x86_cpu_get_pc(CPUState * cs)9136 static vaddr x86_cpu_get_pc(CPUState *cs)
9137 {
9138 X86CPU *cpu = X86_CPU(cs);
9139
9140 /* Match cpu_get_tb_cpu_state. */
9141 return cpu->env.eip + cpu->env.segs[R_CS].base;
9142 }
9143
9144 #if !defined(CONFIG_USER_ONLY)
x86_cpu_pending_interrupt(CPUState * cs,int interrupt_request)9145 int x86_cpu_pending_interrupt(CPUState *cs, int interrupt_request)
9146 {
9147 X86CPU *cpu = X86_CPU(cs);
9148 CPUX86State *env = &cpu->env;
9149
9150 if (interrupt_request & CPU_INTERRUPT_POLL) {
9151 return CPU_INTERRUPT_POLL;
9152 }
9153 if (interrupt_request & CPU_INTERRUPT_SIPI) {
9154 return CPU_INTERRUPT_SIPI;
9155 }
9156
9157 if (env->hflags2 & HF2_GIF_MASK) {
9158 if ((interrupt_request & CPU_INTERRUPT_SMI) &&
9159 !(env->hflags & HF_SMM_MASK)) {
9160 return CPU_INTERRUPT_SMI;
9161 } else if ((interrupt_request & CPU_INTERRUPT_NMI) &&
9162 !(env->hflags2 & HF2_NMI_MASK)) {
9163 return CPU_INTERRUPT_NMI;
9164 } else if (interrupt_request & CPU_INTERRUPT_MCE) {
9165 return CPU_INTERRUPT_MCE;
9166 } else if ((interrupt_request & CPU_INTERRUPT_HARD) &&
9167 (((env->hflags2 & HF2_VINTR_MASK) &&
9168 (env->hflags2 & HF2_HIF_MASK)) ||
9169 (!(env->hflags2 & HF2_VINTR_MASK) &&
9170 (env->eflags & IF_MASK &&
9171 !(env->hflags & HF_INHIBIT_IRQ_MASK))))) {
9172 return CPU_INTERRUPT_HARD;
9173 } else if (env->hflags2 & HF2_VGIF_MASK) {
9174 if((interrupt_request & CPU_INTERRUPT_VIRQ) &&
9175 (env->eflags & IF_MASK) &&
9176 !(env->hflags & HF_INHIBIT_IRQ_MASK)) {
9177 return CPU_INTERRUPT_VIRQ;
9178 }
9179 }
9180 }
9181
9182 return 0;
9183 }
9184
x86_cpu_has_work(CPUState * cs)9185 static bool x86_cpu_has_work(CPUState *cs)
9186 {
9187 return x86_cpu_pending_interrupt(cs, cs->interrupt_request) != 0;
9188 }
9189 #endif /* !CONFIG_USER_ONLY */
9190
x86_disas_set_info(CPUState * cs,disassemble_info * info)9191 static void x86_disas_set_info(CPUState *cs, disassemble_info *info)
9192 {
9193 X86CPU *cpu = X86_CPU(cs);
9194 CPUX86State *env = &cpu->env;
9195
9196 info->endian = BFD_ENDIAN_LITTLE;
9197 info->mach = (env->hflags & HF_CS64_MASK ? bfd_mach_x86_64
9198 : env->hflags & HF_CS32_MASK ? bfd_mach_i386_i386
9199 : bfd_mach_i386_i8086);
9200
9201 info->cap_arch = CS_ARCH_X86;
9202 info->cap_mode = (env->hflags & HF_CS64_MASK ? CS_MODE_64
9203 : env->hflags & HF_CS32_MASK ? CS_MODE_32
9204 : CS_MODE_16);
9205 info->cap_insn_unit = 1;
9206 info->cap_insn_split = 8;
9207 }
9208
x86_update_hflags(CPUX86State * env)9209 void x86_update_hflags(CPUX86State *env)
9210 {
9211 uint32_t hflags;
9212 #define HFLAG_COPY_MASK \
9213 ~( HF_CPL_MASK | HF_PE_MASK | HF_MP_MASK | HF_EM_MASK | \
9214 HF_TS_MASK | HF_TF_MASK | HF_VM_MASK | HF_IOPL_MASK | \
9215 HF_OSFXSR_MASK | HF_LMA_MASK | HF_CS32_MASK | \
9216 HF_SS32_MASK | HF_CS64_MASK | HF_ADDSEG_MASK)
9217
9218 hflags = env->hflags & HFLAG_COPY_MASK;
9219 hflags |= (env->segs[R_SS].flags >> DESC_DPL_SHIFT) & HF_CPL_MASK;
9220 hflags |= (env->cr[0] & CR0_PE_MASK) << (HF_PE_SHIFT - CR0_PE_SHIFT);
9221 hflags |= (env->cr[0] << (HF_MP_SHIFT - CR0_MP_SHIFT)) &
9222 (HF_MP_MASK | HF_EM_MASK | HF_TS_MASK);
9223 hflags |= (env->eflags & (HF_TF_MASK | HF_VM_MASK | HF_IOPL_MASK));
9224
9225 if (env->cr[4] & CR4_OSFXSR_MASK) {
9226 hflags |= HF_OSFXSR_MASK;
9227 }
9228
9229 if (env->efer & MSR_EFER_LMA) {
9230 hflags |= HF_LMA_MASK;
9231 }
9232
9233 if ((hflags & HF_LMA_MASK) && (env->segs[R_CS].flags & DESC_L_MASK)) {
9234 hflags |= HF_CS32_MASK | HF_SS32_MASK | HF_CS64_MASK;
9235 } else {
9236 hflags |= (env->segs[R_CS].flags & DESC_B_MASK) >>
9237 (DESC_B_SHIFT - HF_CS32_SHIFT);
9238 hflags |= (env->segs[R_SS].flags & DESC_B_MASK) >>
9239 (DESC_B_SHIFT - HF_SS32_SHIFT);
9240 if (!(env->cr[0] & CR0_PE_MASK) || (env->eflags & VM_MASK) ||
9241 !(hflags & HF_CS32_MASK)) {
9242 hflags |= HF_ADDSEG_MASK;
9243 } else {
9244 hflags |= ((env->segs[R_DS].base | env->segs[R_ES].base |
9245 env->segs[R_SS].base) != 0) << HF_ADDSEG_SHIFT;
9246 }
9247 }
9248 env->hflags = hflags;
9249 }
9250
9251 static const Property x86_cpu_properties[] = {
9252 #ifdef CONFIG_USER_ONLY
9253 /* apic_id = 0 by default for *-user, see commit 9886e834 */
9254 DEFINE_PROP_UINT32("apic-id", X86CPU, apic_id, 0),
9255 DEFINE_PROP_INT32("thread-id", X86CPU, thread_id, 0),
9256 DEFINE_PROP_INT32("core-id", X86CPU, core_id, 0),
9257 DEFINE_PROP_INT32("module-id", X86CPU, module_id, 0),
9258 DEFINE_PROP_INT32("die-id", X86CPU, die_id, 0),
9259 DEFINE_PROP_INT32("socket-id", X86CPU, socket_id, 0),
9260 #else
9261 DEFINE_PROP_UINT32("apic-id", X86CPU, apic_id, UNASSIGNED_APIC_ID),
9262 DEFINE_PROP_INT32("thread-id", X86CPU, thread_id, -1),
9263 DEFINE_PROP_INT32("core-id", X86CPU, core_id, -1),
9264 DEFINE_PROP_INT32("module-id", X86CPU, module_id, -1),
9265 DEFINE_PROP_INT32("die-id", X86CPU, die_id, -1),
9266 DEFINE_PROP_INT32("socket-id", X86CPU, socket_id, -1),
9267 #endif
9268 DEFINE_PROP_INT32("node-id", X86CPU, node_id, CPU_UNSET_NUMA_NODE_ID),
9269 DEFINE_PROP_BOOL("pmu", X86CPU, enable_pmu, false),
9270 DEFINE_PROP_UINT64_CHECKMASK("lbr-fmt", X86CPU, lbr_fmt, PERF_CAP_LBR_FMT),
9271
9272 DEFINE_PROP_UINT32("hv-spinlocks", X86CPU, hyperv_spinlock_attempts,
9273 HYPERV_SPINLOCK_NEVER_NOTIFY),
9274 DEFINE_PROP_BIT64("hv-relaxed", X86CPU, hyperv_features,
9275 HYPERV_FEAT_RELAXED, 0),
9276 DEFINE_PROP_BIT64("hv-vapic", X86CPU, hyperv_features,
9277 HYPERV_FEAT_VAPIC, 0),
9278 DEFINE_PROP_BIT64("hv-time", X86CPU, hyperv_features,
9279 HYPERV_FEAT_TIME, 0),
9280 DEFINE_PROP_BIT64("hv-crash", X86CPU, hyperv_features,
9281 HYPERV_FEAT_CRASH, 0),
9282 DEFINE_PROP_BIT64("hv-reset", X86CPU, hyperv_features,
9283 HYPERV_FEAT_RESET, 0),
9284 DEFINE_PROP_BIT64("hv-vpindex", X86CPU, hyperv_features,
9285 HYPERV_FEAT_VPINDEX, 0),
9286 DEFINE_PROP_BIT64("hv-runtime", X86CPU, hyperv_features,
9287 HYPERV_FEAT_RUNTIME, 0),
9288 DEFINE_PROP_BIT64("hv-synic", X86CPU, hyperv_features,
9289 HYPERV_FEAT_SYNIC, 0),
9290 DEFINE_PROP_BIT64("hv-stimer", X86CPU, hyperv_features,
9291 HYPERV_FEAT_STIMER, 0),
9292 DEFINE_PROP_BIT64("hv-frequencies", X86CPU, hyperv_features,
9293 HYPERV_FEAT_FREQUENCIES, 0),
9294 DEFINE_PROP_BIT64("hv-reenlightenment", X86CPU, hyperv_features,
9295 HYPERV_FEAT_REENLIGHTENMENT, 0),
9296 DEFINE_PROP_BIT64("hv-tlbflush", X86CPU, hyperv_features,
9297 HYPERV_FEAT_TLBFLUSH, 0),
9298 DEFINE_PROP_BIT64("hv-evmcs", X86CPU, hyperv_features,
9299 HYPERV_FEAT_EVMCS, 0),
9300 DEFINE_PROP_BIT64("hv-ipi", X86CPU, hyperv_features,
9301 HYPERV_FEAT_IPI, 0),
9302 DEFINE_PROP_BIT64("hv-stimer-direct", X86CPU, hyperv_features,
9303 HYPERV_FEAT_STIMER_DIRECT, 0),
9304 DEFINE_PROP_BIT64("hv-avic", X86CPU, hyperv_features,
9305 HYPERV_FEAT_AVIC, 0),
9306 DEFINE_PROP_BIT64("hv-emsr-bitmap", X86CPU, hyperv_features,
9307 HYPERV_FEAT_MSR_BITMAP, 0),
9308 DEFINE_PROP_BIT64("hv-xmm-input", X86CPU, hyperv_features,
9309 HYPERV_FEAT_XMM_INPUT, 0),
9310 DEFINE_PROP_BIT64("hv-tlbflush-ext", X86CPU, hyperv_features,
9311 HYPERV_FEAT_TLBFLUSH_EXT, 0),
9312 DEFINE_PROP_BIT64("hv-tlbflush-direct", X86CPU, hyperv_features,
9313 HYPERV_FEAT_TLBFLUSH_DIRECT, 0),
9314 DEFINE_PROP_ON_OFF_AUTO("hv-no-nonarch-coresharing", X86CPU,
9315 hyperv_no_nonarch_cs, ON_OFF_AUTO_OFF),
9316 #ifdef CONFIG_SYNDBG
9317 DEFINE_PROP_BIT64("hv-syndbg", X86CPU, hyperv_features,
9318 HYPERV_FEAT_SYNDBG, 0),
9319 #endif
9320 DEFINE_PROP_BOOL("hv-passthrough", X86CPU, hyperv_passthrough, false),
9321 DEFINE_PROP_BOOL("hv-enforce-cpuid", X86CPU, hyperv_enforce_cpuid, false),
9322
9323 /* WS2008R2 identify by default */
9324 DEFINE_PROP_UINT32("hv-version-id-build", X86CPU, hyperv_ver_id_build,
9325 0x3839),
9326 DEFINE_PROP_UINT16("hv-version-id-major", X86CPU, hyperv_ver_id_major,
9327 0x000A),
9328 DEFINE_PROP_UINT16("hv-version-id-minor", X86CPU, hyperv_ver_id_minor,
9329 0x0000),
9330 DEFINE_PROP_UINT32("hv-version-id-spack", X86CPU, hyperv_ver_id_sp, 0),
9331 DEFINE_PROP_UINT8("hv-version-id-sbranch", X86CPU, hyperv_ver_id_sb, 0),
9332 DEFINE_PROP_UINT32("hv-version-id-snumber", X86CPU, hyperv_ver_id_sn, 0),
9333
9334 DEFINE_PROP_BOOL("check", X86CPU, check_cpuid, true),
9335 DEFINE_PROP_BOOL("enforce", X86CPU, enforce_cpuid, false),
9336 DEFINE_PROP_BOOL("x-force-features", X86CPU, force_features, false),
9337 DEFINE_PROP_BOOL("kvm", X86CPU, expose_kvm, true),
9338 DEFINE_PROP_UINT32("phys-bits", X86CPU, phys_bits, 0),
9339 DEFINE_PROP_UINT32("guest-phys-bits", X86CPU, guest_phys_bits, -1),
9340 DEFINE_PROP_BOOL("host-phys-bits", X86CPU, host_phys_bits, false),
9341 DEFINE_PROP_UINT8("host-phys-bits-limit", X86CPU, host_phys_bits_limit, 0),
9342 DEFINE_PROP_BOOL("fill-mtrr-mask", X86CPU, fill_mtrr_mask, true),
9343 DEFINE_PROP_UINT32("level-func7", X86CPU, env.cpuid_level_func7,
9344 UINT32_MAX),
9345 DEFINE_PROP_UINT32("level", X86CPU, env.cpuid_level, UINT32_MAX),
9346 DEFINE_PROP_UINT32("xlevel", X86CPU, env.cpuid_xlevel, UINT32_MAX),
9347 DEFINE_PROP_UINT32("xlevel2", X86CPU, env.cpuid_xlevel2, UINT32_MAX),
9348 DEFINE_PROP_UINT32("min-level", X86CPU, env.cpuid_min_level, 0),
9349 DEFINE_PROP_UINT32("min-xlevel", X86CPU, env.cpuid_min_xlevel, 0),
9350 DEFINE_PROP_UINT32("min-xlevel2", X86CPU, env.cpuid_min_xlevel2, 0),
9351 DEFINE_PROP_UINT8("avx10-version", X86CPU, env.avx10_version, 0),
9352 DEFINE_PROP_UINT64("ucode-rev", X86CPU, ucode_rev, 0),
9353 DEFINE_PROP_BOOL("full-cpuid-auto-level", X86CPU, full_cpuid_auto_level, true),
9354 DEFINE_PROP_STRING("hv-vendor-id", X86CPU, hyperv_vendor),
9355 DEFINE_PROP_BOOL("cpuid-0xb", X86CPU, enable_cpuid_0xb, true),
9356 DEFINE_PROP_BOOL("x-vendor-cpuid-only", X86CPU, vendor_cpuid_only, true),
9357 DEFINE_PROP_BOOL("x-amd-topoext-features-only", X86CPU, amd_topoext_features_only, true),
9358 DEFINE_PROP_BOOL("lmce", X86CPU, enable_lmce, false),
9359 DEFINE_PROP_BOOL("l3-cache", X86CPU, enable_l3_cache, true),
9360 DEFINE_PROP_BOOL("kvm-pv-enforce-cpuid", X86CPU, kvm_pv_enforce_cpuid,
9361 false),
9362 DEFINE_PROP_BOOL("vmware-cpuid-freq", X86CPU, vmware_cpuid_freq, true),
9363 DEFINE_PROP_BOOL("tcg-cpuid", X86CPU, expose_tcg, true),
9364 DEFINE_PROP_BOOL("x-migrate-smi-count", X86CPU, migrate_smi_count,
9365 true),
9366 /*
9367 * lecacy_cache defaults to true unless the CPU model provides its
9368 * own cache information (see x86_cpu_load_def()).
9369 */
9370 DEFINE_PROP_BOOL("legacy-cache", X86CPU, legacy_cache, true),
9371 DEFINE_PROP_BOOL("legacy-multi-node", X86CPU, legacy_multi_node, false),
9372 DEFINE_PROP_BOOL("xen-vapic", X86CPU, xen_vapic, false),
9373
9374 /*
9375 * From "Requirements for Implementing the Microsoft
9376 * Hypervisor Interface":
9377 * https://docs.microsoft.com/en-us/virtualization/hyper-v-on-windows/reference/tlfs
9378 *
9379 * "Starting with Windows Server 2012 and Windows 8, if
9380 * CPUID.40000005.EAX contains a value of -1, Windows assumes that
9381 * the hypervisor imposes no specific limit to the number of VPs.
9382 * In this case, Windows Server 2012 guest VMs may use more than
9383 * 64 VPs, up to the maximum supported number of processors applicable
9384 * to the specific Windows version being used."
9385 */
9386 DEFINE_PROP_INT32("x-hv-max-vps", X86CPU, hv_max_vps, -1),
9387 DEFINE_PROP_BOOL("x-hv-synic-kvm-only", X86CPU, hyperv_synic_kvm_only,
9388 false),
9389 DEFINE_PROP_BOOL("x-intel-pt-auto-level", X86CPU, intel_pt_auto_level,
9390 true),
9391 DEFINE_PROP_BOOL("x-l1-cache-per-thread", X86CPU, l1_cache_per_core, true),
9392 };
9393
9394 #ifndef CONFIG_USER_ONLY
9395 #include "hw/core/sysemu-cpu-ops.h"
9396
9397 static const struct SysemuCPUOps i386_sysemu_ops = {
9398 .has_work = x86_cpu_has_work,
9399 .get_memory_mapping = x86_cpu_get_memory_mapping,
9400 .get_paging_enabled = x86_cpu_get_paging_enabled,
9401 .get_phys_page_attrs_debug = x86_cpu_get_phys_page_attrs_debug,
9402 .asidx_from_attrs = x86_asidx_from_attrs,
9403 .get_crash_info = x86_cpu_get_crash_info,
9404 .write_elf32_note = x86_cpu_write_elf32_note,
9405 .write_elf64_note = x86_cpu_write_elf64_note,
9406 .write_elf32_qemunote = x86_cpu_write_elf32_qemunote,
9407 .write_elf64_qemunote = x86_cpu_write_elf64_qemunote,
9408 .legacy_vmsd = &vmstate_x86_cpu,
9409 };
9410 #endif
9411
x86_cpu_common_class_init(ObjectClass * oc,const void * data)9412 static void x86_cpu_common_class_init(ObjectClass *oc, const void *data)
9413 {
9414 X86CPUClass *xcc = X86_CPU_CLASS(oc);
9415 CPUClass *cc = CPU_CLASS(oc);
9416 DeviceClass *dc = DEVICE_CLASS(oc);
9417 ResettableClass *rc = RESETTABLE_CLASS(oc);
9418 FeatureWord w;
9419
9420 device_class_set_parent_realize(dc, x86_cpu_realizefn,
9421 &xcc->parent_realize);
9422 device_class_set_parent_unrealize(dc, x86_cpu_unrealizefn,
9423 &xcc->parent_unrealize);
9424 device_class_set_props(dc, x86_cpu_properties);
9425
9426 resettable_class_set_parent_phases(rc, NULL, x86_cpu_reset_hold, NULL,
9427 &xcc->parent_phases);
9428 cc->reset_dump_flags = CPU_DUMP_FPU | CPU_DUMP_CCOP;
9429
9430 cc->class_by_name = x86_cpu_class_by_name;
9431 cc->list_cpus = x86_cpu_list;
9432 cc->parse_features = x86_cpu_parse_featurestr;
9433 cc->dump_state = x86_cpu_dump_state;
9434 cc->set_pc = x86_cpu_set_pc;
9435 cc->get_pc = x86_cpu_get_pc;
9436 cc->gdb_read_register = x86_cpu_gdb_read_register;
9437 cc->gdb_write_register = x86_cpu_gdb_write_register;
9438 cc->get_arch_id = x86_cpu_get_arch_id;
9439
9440 #ifndef CONFIG_USER_ONLY
9441 cc->sysemu_ops = &i386_sysemu_ops;
9442 #endif /* !CONFIG_USER_ONLY */
9443 #ifdef CONFIG_TCG
9444 cc->tcg_ops = &x86_tcg_ops;
9445 #endif /* CONFIG_TCG */
9446
9447 cc->gdb_arch_name = x86_gdb_arch_name;
9448 #ifdef TARGET_X86_64
9449 cc->gdb_core_xml_file = "i386-64bit.xml";
9450 #else
9451 cc->gdb_core_xml_file = "i386-32bit.xml";
9452 #endif
9453 cc->disas_set_info = x86_disas_set_info;
9454
9455 dc->user_creatable = true;
9456
9457 object_class_property_add(oc, "family", "int",
9458 x86_cpuid_version_get_family,
9459 x86_cpuid_version_set_family, NULL, NULL);
9460 object_class_property_add(oc, "model", "int",
9461 x86_cpuid_version_get_model,
9462 x86_cpuid_version_set_model, NULL, NULL);
9463 object_class_property_add(oc, "stepping", "int",
9464 x86_cpuid_version_get_stepping,
9465 x86_cpuid_version_set_stepping, NULL, NULL);
9466 object_class_property_add_str(oc, "vendor",
9467 x86_cpuid_get_vendor,
9468 x86_cpuid_set_vendor);
9469 object_class_property_add_str(oc, "model-id",
9470 x86_cpuid_get_model_id,
9471 x86_cpuid_set_model_id);
9472 object_class_property_add(oc, "tsc-frequency", "int",
9473 x86_cpuid_get_tsc_freq,
9474 x86_cpuid_set_tsc_freq, NULL, NULL);
9475 /*
9476 * The "unavailable-features" property has the same semantics as
9477 * CpuDefinitionInfo.unavailable-features on the "query-cpu-definitions"
9478 * QMP command: they list the features that would have prevented the
9479 * CPU from running if the "enforce" flag was set.
9480 */
9481 object_class_property_add(oc, "unavailable-features", "strList",
9482 x86_cpu_get_unavailable_features,
9483 NULL, NULL, NULL);
9484
9485 #if !defined(CONFIG_USER_ONLY)
9486 object_class_property_add(oc, "crash-information", "GuestPanicInformation",
9487 x86_cpu_get_crash_info_qom, NULL, NULL, NULL);
9488 #endif
9489
9490 for (w = 0; w < FEATURE_WORDS; w++) {
9491 int bitnr;
9492 for (bitnr = 0; bitnr < 64; bitnr++) {
9493 x86_cpu_register_feature_bit_props(xcc, w, bitnr);
9494 }
9495 }
9496 }
9497
9498 static const TypeInfo x86_cpu_type_info = {
9499 .name = TYPE_X86_CPU,
9500 .parent = TYPE_CPU,
9501 .instance_size = sizeof(X86CPU),
9502 .instance_align = __alignof(X86CPU),
9503 .instance_init = x86_cpu_initfn,
9504 .instance_post_init = x86_cpu_post_initfn,
9505
9506 .abstract = true,
9507 .class_size = sizeof(X86CPUClass),
9508 .class_init = x86_cpu_common_class_init,
9509 };
9510
9511 /* "base" CPU model, used by query-cpu-model-expansion */
x86_cpu_base_class_init(ObjectClass * oc,const void * data)9512 static void x86_cpu_base_class_init(ObjectClass *oc, const void *data)
9513 {
9514 X86CPUClass *xcc = X86_CPU_CLASS(oc);
9515
9516 xcc->static_model = true;
9517 xcc->migration_safe = true;
9518 xcc->model_description = "base CPU model type with no features enabled";
9519 xcc->ordering = 8;
9520 }
9521
9522 static const TypeInfo x86_base_cpu_type_info = {
9523 .name = X86_CPU_TYPE_NAME("base"),
9524 .parent = TYPE_X86_CPU,
9525 .class_init = x86_cpu_base_class_init,
9526 };
9527
x86_cpu_register_types(void)9528 static void x86_cpu_register_types(void)
9529 {
9530 int i;
9531
9532 type_register_static(&x86_cpu_type_info);
9533 for (i = 0; i < ARRAY_SIZE(builtin_x86_defs); i++) {
9534 x86_register_cpudef_types(&builtin_x86_defs[i]);
9535 }
9536 type_register_static(&max_x86_cpu_type_info);
9537 type_register_static(&x86_base_cpu_type_info);
9538 }
9539
9540 type_init(x86_cpu_register_types)
9541