qtest/libqos: add a function to initialize secondary PCI buses
[qemu/ar7.git] / target / i386 / cpu.c
blobaa9e6368004c7490ea63cc28ee3f9fe498771899
1 /*
2 * i386 CPUID, CPU class, definitions, models
4 * Copyright (c) 2003 Fabrice Bellard
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.
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.
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/>.
20 #include "qemu/osdep.h"
21 #include "qemu/units.h"
22 #include "qemu/cutils.h"
23 #include "qemu/qemu-print.h"
24 #include "cpu.h"
25 #include "tcg/helper-tcg.h"
26 #include "sysemu/reset.h"
27 #include "sysemu/hvf.h"
28 #include "kvm/kvm_i386.h"
29 #include "sev.h"
30 #include "qapi/error.h"
31 #include "qapi/qapi-visit-machine.h"
32 #include "qapi/qmp/qerror.h"
33 #include "qapi/qapi-commands-machine-target.h"
34 #include "standard-headers/asm-x86/kvm_para.h"
35 #include "hw/qdev-properties.h"
36 #include "hw/i386/topology.h"
37 #ifndef CONFIG_USER_ONLY
38 #include "exec/address-spaces.h"
39 #include "hw/boards.h"
40 #include "hw/i386/sgx-epc.h"
41 #endif
43 #include "disas/capstone.h"
44 #include "cpu-internal.h"
46 /* Helpers for building CPUID[2] descriptors: */
48 struct CPUID2CacheDescriptorInfo {
49 enum CacheType type;
50 int level;
51 int size;
52 int line_size;
53 int associativity;
57 * Known CPUID 2 cache descriptors.
58 * From Intel SDM Volume 2A, CPUID instruction
60 struct CPUID2CacheDescriptorInfo cpuid2_cache_descriptors[] = {
61 [0x06] = { .level = 1, .type = INSTRUCTION_CACHE, .size = 8 * KiB,
62 .associativity = 4, .line_size = 32, },
63 [0x08] = { .level = 1, .type = INSTRUCTION_CACHE, .size = 16 * KiB,
64 .associativity = 4, .line_size = 32, },
65 [0x09] = { .level = 1, .type = INSTRUCTION_CACHE, .size = 32 * KiB,
66 .associativity = 4, .line_size = 64, },
67 [0x0A] = { .level = 1, .type = DATA_CACHE, .size = 8 * KiB,
68 .associativity = 2, .line_size = 32, },
69 [0x0C] = { .level = 1, .type = DATA_CACHE, .size = 16 * KiB,
70 .associativity = 4, .line_size = 32, },
71 [0x0D] = { .level = 1, .type = DATA_CACHE, .size = 16 * KiB,
72 .associativity = 4, .line_size = 64, },
73 [0x0E] = { .level = 1, .type = DATA_CACHE, .size = 24 * KiB,
74 .associativity = 6, .line_size = 64, },
75 [0x1D] = { .level = 2, .type = UNIFIED_CACHE, .size = 128 * KiB,
76 .associativity = 2, .line_size = 64, },
77 [0x21] = { .level = 2, .type = UNIFIED_CACHE, .size = 256 * KiB,
78 .associativity = 8, .line_size = 64, },
79 /* lines per sector is not supported cpuid2_cache_descriptor(),
80 * so descriptors 0x22, 0x23 are not included
82 [0x24] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
83 .associativity = 16, .line_size = 64, },
84 /* lines per sector is not supported cpuid2_cache_descriptor(),
85 * so descriptors 0x25, 0x20 are not included
87 [0x2C] = { .level = 1, .type = DATA_CACHE, .size = 32 * KiB,
88 .associativity = 8, .line_size = 64, },
89 [0x30] = { .level = 1, .type = INSTRUCTION_CACHE, .size = 32 * KiB,
90 .associativity = 8, .line_size = 64, },
91 [0x41] = { .level = 2, .type = UNIFIED_CACHE, .size = 128 * KiB,
92 .associativity = 4, .line_size = 32, },
93 [0x42] = { .level = 2, .type = UNIFIED_CACHE, .size = 256 * KiB,
94 .associativity = 4, .line_size = 32, },
95 [0x43] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
96 .associativity = 4, .line_size = 32, },
97 [0x44] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
98 .associativity = 4, .line_size = 32, },
99 [0x45] = { .level = 2, .type = UNIFIED_CACHE, .size = 2 * MiB,
100 .associativity = 4, .line_size = 32, },
101 [0x46] = { .level = 3, .type = UNIFIED_CACHE, .size = 4 * MiB,
102 .associativity = 4, .line_size = 64, },
103 [0x47] = { .level = 3, .type = UNIFIED_CACHE, .size = 8 * MiB,
104 .associativity = 8, .line_size = 64, },
105 [0x48] = { .level = 2, .type = UNIFIED_CACHE, .size = 3 * MiB,
106 .associativity = 12, .line_size = 64, },
107 /* Descriptor 0x49 depends on CPU family/model, so it is not included */
108 [0x4A] = { .level = 3, .type = UNIFIED_CACHE, .size = 6 * MiB,
109 .associativity = 12, .line_size = 64, },
110 [0x4B] = { .level = 3, .type = UNIFIED_CACHE, .size = 8 * MiB,
111 .associativity = 16, .line_size = 64, },
112 [0x4C] = { .level = 3, .type = UNIFIED_CACHE, .size = 12 * MiB,
113 .associativity = 12, .line_size = 64, },
114 [0x4D] = { .level = 3, .type = UNIFIED_CACHE, .size = 16 * MiB,
115 .associativity = 16, .line_size = 64, },
116 [0x4E] = { .level = 2, .type = UNIFIED_CACHE, .size = 6 * MiB,
117 .associativity = 24, .line_size = 64, },
118 [0x60] = { .level = 1, .type = DATA_CACHE, .size = 16 * KiB,
119 .associativity = 8, .line_size = 64, },
120 [0x66] = { .level = 1, .type = DATA_CACHE, .size = 8 * KiB,
121 .associativity = 4, .line_size = 64, },
122 [0x67] = { .level = 1, .type = DATA_CACHE, .size = 16 * KiB,
123 .associativity = 4, .line_size = 64, },
124 [0x68] = { .level = 1, .type = DATA_CACHE, .size = 32 * KiB,
125 .associativity = 4, .line_size = 64, },
126 [0x78] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
127 .associativity = 4, .line_size = 64, },
128 /* lines per sector is not supported cpuid2_cache_descriptor(),
129 * so descriptors 0x79, 0x7A, 0x7B, 0x7C are not included.
131 [0x7D] = { .level = 2, .type = UNIFIED_CACHE, .size = 2 * MiB,
132 .associativity = 8, .line_size = 64, },
133 [0x7F] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
134 .associativity = 2, .line_size = 64, },
135 [0x80] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
136 .associativity = 8, .line_size = 64, },
137 [0x82] = { .level = 2, .type = UNIFIED_CACHE, .size = 256 * KiB,
138 .associativity = 8, .line_size = 32, },
139 [0x83] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
140 .associativity = 8, .line_size = 32, },
141 [0x84] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
142 .associativity = 8, .line_size = 32, },
143 [0x85] = { .level = 2, .type = UNIFIED_CACHE, .size = 2 * MiB,
144 .associativity = 8, .line_size = 32, },
145 [0x86] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
146 .associativity = 4, .line_size = 64, },
147 [0x87] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
148 .associativity = 8, .line_size = 64, },
149 [0xD0] = { .level = 3, .type = UNIFIED_CACHE, .size = 512 * KiB,
150 .associativity = 4, .line_size = 64, },
151 [0xD1] = { .level = 3, .type = UNIFIED_CACHE, .size = 1 * MiB,
152 .associativity = 4, .line_size = 64, },
153 [0xD2] = { .level = 3, .type = UNIFIED_CACHE, .size = 2 * MiB,
154 .associativity = 4, .line_size = 64, },
155 [0xD6] = { .level = 3, .type = UNIFIED_CACHE, .size = 1 * MiB,
156 .associativity = 8, .line_size = 64, },
157 [0xD7] = { .level = 3, .type = UNIFIED_CACHE, .size = 2 * MiB,
158 .associativity = 8, .line_size = 64, },
159 [0xD8] = { .level = 3, .type = UNIFIED_CACHE, .size = 4 * MiB,
160 .associativity = 8, .line_size = 64, },
161 [0xDC] = { .level = 3, .type = UNIFIED_CACHE, .size = 1.5 * MiB,
162 .associativity = 12, .line_size = 64, },
163 [0xDD] = { .level = 3, .type = UNIFIED_CACHE, .size = 3 * MiB,
164 .associativity = 12, .line_size = 64, },
165 [0xDE] = { .level = 3, .type = UNIFIED_CACHE, .size = 6 * MiB,
166 .associativity = 12, .line_size = 64, },
167 [0xE2] = { .level = 3, .type = UNIFIED_CACHE, .size = 2 * MiB,
168 .associativity = 16, .line_size = 64, },
169 [0xE3] = { .level = 3, .type = UNIFIED_CACHE, .size = 4 * MiB,
170 .associativity = 16, .line_size = 64, },
171 [0xE4] = { .level = 3, .type = UNIFIED_CACHE, .size = 8 * MiB,
172 .associativity = 16, .line_size = 64, },
173 [0xEA] = { .level = 3, .type = UNIFIED_CACHE, .size = 12 * MiB,
174 .associativity = 24, .line_size = 64, },
175 [0xEB] = { .level = 3, .type = UNIFIED_CACHE, .size = 18 * MiB,
176 .associativity = 24, .line_size = 64, },
177 [0xEC] = { .level = 3, .type = UNIFIED_CACHE, .size = 24 * MiB,
178 .associativity = 24, .line_size = 64, },
182 * "CPUID leaf 2 does not report cache descriptor information,
183 * use CPUID leaf 4 to query cache parameters"
185 #define CACHE_DESCRIPTOR_UNAVAILABLE 0xFF
188 * Return a CPUID 2 cache descriptor for a given cache.
189 * If no known descriptor is found, return CACHE_DESCRIPTOR_UNAVAILABLE
191 static uint8_t cpuid2_cache_descriptor(CPUCacheInfo *cache)
193 int i;
195 assert(cache->size > 0);
196 assert(cache->level > 0);
197 assert(cache->line_size > 0);
198 assert(cache->associativity > 0);
199 for (i = 0; i < ARRAY_SIZE(cpuid2_cache_descriptors); i++) {
200 struct CPUID2CacheDescriptorInfo *d = &cpuid2_cache_descriptors[i];
201 if (d->level == cache->level && d->type == cache->type &&
202 d->size == cache->size && d->line_size == cache->line_size &&
203 d->associativity == cache->associativity) {
204 return i;
208 return CACHE_DESCRIPTOR_UNAVAILABLE;
211 /* CPUID Leaf 4 constants: */
213 /* EAX: */
214 #define CACHE_TYPE_D 1
215 #define CACHE_TYPE_I 2
216 #define CACHE_TYPE_UNIFIED 3
218 #define CACHE_LEVEL(l) (l << 5)
220 #define CACHE_SELF_INIT_LEVEL (1 << 8)
222 /* EDX: */
223 #define CACHE_NO_INVD_SHARING (1 << 0)
224 #define CACHE_INCLUSIVE (1 << 1)
225 #define CACHE_COMPLEX_IDX (1 << 2)
227 /* Encode CacheType for CPUID[4].EAX */
228 #define CACHE_TYPE(t) (((t) == DATA_CACHE) ? CACHE_TYPE_D : \
229 ((t) == INSTRUCTION_CACHE) ? CACHE_TYPE_I : \
230 ((t) == UNIFIED_CACHE) ? CACHE_TYPE_UNIFIED : \
231 0 /* Invalid value */)
234 /* Encode cache info for CPUID[4] */
235 static void encode_cache_cpuid4(CPUCacheInfo *cache,
236 int num_apic_ids, int num_cores,
237 uint32_t *eax, uint32_t *ebx,
238 uint32_t *ecx, uint32_t *edx)
240 assert(cache->size == cache->line_size * cache->associativity *
241 cache->partitions * cache->sets);
243 assert(num_apic_ids > 0);
244 *eax = CACHE_TYPE(cache->type) |
245 CACHE_LEVEL(cache->level) |
246 (cache->self_init ? CACHE_SELF_INIT_LEVEL : 0) |
247 ((num_cores - 1) << 26) |
248 ((num_apic_ids - 1) << 14);
250 assert(cache->line_size > 0);
251 assert(cache->partitions > 0);
252 assert(cache->associativity > 0);
253 /* We don't implement fully-associative caches */
254 assert(cache->associativity < cache->sets);
255 *ebx = (cache->line_size - 1) |
256 ((cache->partitions - 1) << 12) |
257 ((cache->associativity - 1) << 22);
259 assert(cache->sets > 0);
260 *ecx = cache->sets - 1;
262 *edx = (cache->no_invd_sharing ? CACHE_NO_INVD_SHARING : 0) |
263 (cache->inclusive ? CACHE_INCLUSIVE : 0) |
264 (cache->complex_indexing ? CACHE_COMPLEX_IDX : 0);
267 /* Encode cache info for CPUID[0x80000005].ECX or CPUID[0x80000005].EDX */
268 static uint32_t encode_cache_cpuid80000005(CPUCacheInfo *cache)
270 assert(cache->size % 1024 == 0);
271 assert(cache->lines_per_tag > 0);
272 assert(cache->associativity > 0);
273 assert(cache->line_size > 0);
274 return ((cache->size / 1024) << 24) | (cache->associativity << 16) |
275 (cache->lines_per_tag << 8) | (cache->line_size);
278 #define ASSOC_FULL 0xFF
280 /* AMD associativity encoding used on CPUID Leaf 0x80000006: */
281 #define AMD_ENC_ASSOC(a) (a <= 1 ? a : \
282 a == 2 ? 0x2 : \
283 a == 4 ? 0x4 : \
284 a == 8 ? 0x6 : \
285 a == 16 ? 0x8 : \
286 a == 32 ? 0xA : \
287 a == 48 ? 0xB : \
288 a == 64 ? 0xC : \
289 a == 96 ? 0xD : \
290 a == 128 ? 0xE : \
291 a == ASSOC_FULL ? 0xF : \
292 0 /* invalid value */)
295 * Encode cache info for CPUID[0x80000006].ECX and CPUID[0x80000006].EDX
296 * @l3 can be NULL.
298 static void encode_cache_cpuid80000006(CPUCacheInfo *l2,
299 CPUCacheInfo *l3,
300 uint32_t *ecx, uint32_t *edx)
302 assert(l2->size % 1024 == 0);
303 assert(l2->associativity > 0);
304 assert(l2->lines_per_tag > 0);
305 assert(l2->line_size > 0);
306 *ecx = ((l2->size / 1024) << 16) |
307 (AMD_ENC_ASSOC(l2->associativity) << 12) |
308 (l2->lines_per_tag << 8) | (l2->line_size);
310 if (l3) {
311 assert(l3->size % (512 * 1024) == 0);
312 assert(l3->associativity > 0);
313 assert(l3->lines_per_tag > 0);
314 assert(l3->line_size > 0);
315 *edx = ((l3->size / (512 * 1024)) << 18) |
316 (AMD_ENC_ASSOC(l3->associativity) << 12) |
317 (l3->lines_per_tag << 8) | (l3->line_size);
318 } else {
319 *edx = 0;
323 /* Encode cache info for CPUID[8000001D] */
324 static void encode_cache_cpuid8000001d(CPUCacheInfo *cache,
325 X86CPUTopoInfo *topo_info,
326 uint32_t *eax, uint32_t *ebx,
327 uint32_t *ecx, uint32_t *edx)
329 uint32_t l3_threads;
330 assert(cache->size == cache->line_size * cache->associativity *
331 cache->partitions * cache->sets);
333 *eax = CACHE_TYPE(cache->type) | CACHE_LEVEL(cache->level) |
334 (cache->self_init ? CACHE_SELF_INIT_LEVEL : 0);
336 /* L3 is shared among multiple cores */
337 if (cache->level == 3) {
338 l3_threads = topo_info->cores_per_die * topo_info->threads_per_core;
339 *eax |= (l3_threads - 1) << 14;
340 } else {
341 *eax |= ((topo_info->threads_per_core - 1) << 14);
344 assert(cache->line_size > 0);
345 assert(cache->partitions > 0);
346 assert(cache->associativity > 0);
347 /* We don't implement fully-associative caches */
348 assert(cache->associativity < cache->sets);
349 *ebx = (cache->line_size - 1) |
350 ((cache->partitions - 1) << 12) |
351 ((cache->associativity - 1) << 22);
353 assert(cache->sets > 0);
354 *ecx = cache->sets - 1;
356 *edx = (cache->no_invd_sharing ? CACHE_NO_INVD_SHARING : 0) |
357 (cache->inclusive ? CACHE_INCLUSIVE : 0) |
358 (cache->complex_indexing ? CACHE_COMPLEX_IDX : 0);
361 /* Encode cache info for CPUID[8000001E] */
362 static void encode_topo_cpuid8000001e(X86CPU *cpu, X86CPUTopoInfo *topo_info,
363 uint32_t *eax, uint32_t *ebx,
364 uint32_t *ecx, uint32_t *edx)
366 X86CPUTopoIDs topo_ids;
368 x86_topo_ids_from_apicid(cpu->apic_id, topo_info, &topo_ids);
370 *eax = cpu->apic_id;
373 * CPUID_Fn8000001E_EBX [Core Identifiers] (CoreId)
374 * Read-only. Reset: 0000_XXXXh.
375 * See Core::X86::Cpuid::ExtApicId.
376 * Core::X86::Cpuid::CoreId_lthree[1:0]_core[3:0]_thread[1:0];
377 * Bits Description
378 * 31:16 Reserved.
379 * 15:8 ThreadsPerCore: threads per core. Read-only. Reset: XXh.
380 * The number of threads per core is ThreadsPerCore+1.
381 * 7:0 CoreId: core ID. Read-only. Reset: XXh.
383 * NOTE: CoreId is already part of apic_id. Just use it. We can
384 * use all the 8 bits to represent the core_id here.
386 *ebx = ((topo_info->threads_per_core - 1) << 8) | (topo_ids.core_id & 0xFF);
389 * CPUID_Fn8000001E_ECX [Node Identifiers] (NodeId)
390 * Read-only. Reset: 0000_0XXXh.
391 * Core::X86::Cpuid::NodeId_lthree[1:0]_core[3:0]_thread[1:0];
392 * Bits Description
393 * 31:11 Reserved.
394 * 10:8 NodesPerProcessor: Node per processor. Read-only. Reset: XXXb.
395 * ValidValues:
396 * Value Description
397 * 000b 1 node per processor.
398 * 001b 2 nodes per processor.
399 * 010b Reserved.
400 * 011b 4 nodes per processor.
401 * 111b-100b Reserved.
402 * 7:0 NodeId: Node ID. Read-only. Reset: XXh.
404 * NOTE: Hardware reserves 3 bits for number of nodes per processor.
405 * But users can create more nodes than the actual hardware can
406 * support. To genaralize we can use all the upper 8 bits for nodes.
407 * NodeId is combination of node and socket_id which is already decoded
408 * in apic_id. Just use it by shifting.
410 *ecx = ((topo_info->dies_per_pkg - 1) << 8) |
411 ((cpu->apic_id >> apicid_die_offset(topo_info)) & 0xFF);
413 *edx = 0;
417 * Definitions of the hardcoded cache entries we expose:
418 * These are legacy cache values. If there is a need to change any
419 * of these values please use builtin_x86_defs
422 /* L1 data cache: */
423 static CPUCacheInfo legacy_l1d_cache = {
424 .type = DATA_CACHE,
425 .level = 1,
426 .size = 32 * KiB,
427 .self_init = 1,
428 .line_size = 64,
429 .associativity = 8,
430 .sets = 64,
431 .partitions = 1,
432 .no_invd_sharing = true,
435 /*FIXME: CPUID leaf 0x80000005 is inconsistent with leaves 2 & 4 */
436 static CPUCacheInfo legacy_l1d_cache_amd = {
437 .type = DATA_CACHE,
438 .level = 1,
439 .size = 64 * KiB,
440 .self_init = 1,
441 .line_size = 64,
442 .associativity = 2,
443 .sets = 512,
444 .partitions = 1,
445 .lines_per_tag = 1,
446 .no_invd_sharing = true,
449 /* L1 instruction cache: */
450 static CPUCacheInfo legacy_l1i_cache = {
451 .type = INSTRUCTION_CACHE,
452 .level = 1,
453 .size = 32 * KiB,
454 .self_init = 1,
455 .line_size = 64,
456 .associativity = 8,
457 .sets = 64,
458 .partitions = 1,
459 .no_invd_sharing = true,
462 /*FIXME: CPUID leaf 0x80000005 is inconsistent with leaves 2 & 4 */
463 static CPUCacheInfo legacy_l1i_cache_amd = {
464 .type = INSTRUCTION_CACHE,
465 .level = 1,
466 .size = 64 * KiB,
467 .self_init = 1,
468 .line_size = 64,
469 .associativity = 2,
470 .sets = 512,
471 .partitions = 1,
472 .lines_per_tag = 1,
473 .no_invd_sharing = true,
476 /* Level 2 unified cache: */
477 static CPUCacheInfo legacy_l2_cache = {
478 .type = UNIFIED_CACHE,
479 .level = 2,
480 .size = 4 * MiB,
481 .self_init = 1,
482 .line_size = 64,
483 .associativity = 16,
484 .sets = 4096,
485 .partitions = 1,
486 .no_invd_sharing = true,
489 /*FIXME: CPUID leaf 2 descriptor is inconsistent with CPUID leaf 4 */
490 static CPUCacheInfo legacy_l2_cache_cpuid2 = {
491 .type = UNIFIED_CACHE,
492 .level = 2,
493 .size = 2 * MiB,
494 .line_size = 64,
495 .associativity = 8,
499 /*FIXME: CPUID leaf 0x80000006 is inconsistent with leaves 2 & 4 */
500 static CPUCacheInfo legacy_l2_cache_amd = {
501 .type = UNIFIED_CACHE,
502 .level = 2,
503 .size = 512 * KiB,
504 .line_size = 64,
505 .lines_per_tag = 1,
506 .associativity = 16,
507 .sets = 512,
508 .partitions = 1,
511 /* Level 3 unified cache: */
512 static CPUCacheInfo legacy_l3_cache = {
513 .type = UNIFIED_CACHE,
514 .level = 3,
515 .size = 16 * MiB,
516 .line_size = 64,
517 .associativity = 16,
518 .sets = 16384,
519 .partitions = 1,
520 .lines_per_tag = 1,
521 .self_init = true,
522 .inclusive = true,
523 .complex_indexing = true,
526 /* TLB definitions: */
528 #define L1_DTLB_2M_ASSOC 1
529 #define L1_DTLB_2M_ENTRIES 255
530 #define L1_DTLB_4K_ASSOC 1
531 #define L1_DTLB_4K_ENTRIES 255
533 #define L1_ITLB_2M_ASSOC 1
534 #define L1_ITLB_2M_ENTRIES 255
535 #define L1_ITLB_4K_ASSOC 1
536 #define L1_ITLB_4K_ENTRIES 255
538 #define L2_DTLB_2M_ASSOC 0 /* disabled */
539 #define L2_DTLB_2M_ENTRIES 0 /* disabled */
540 #define L2_DTLB_4K_ASSOC 4
541 #define L2_DTLB_4K_ENTRIES 512
543 #define L2_ITLB_2M_ASSOC 0 /* disabled */
544 #define L2_ITLB_2M_ENTRIES 0 /* disabled */
545 #define L2_ITLB_4K_ASSOC 4
546 #define L2_ITLB_4K_ENTRIES 512
548 /* CPUID Leaf 0x14 constants: */
549 #define INTEL_PT_MAX_SUBLEAF 0x1
551 * bit[00]: IA32_RTIT_CTL.CR3 filter can be set to 1 and IA32_RTIT_CR3_MATCH
552 * MSR can be accessed;
553 * bit[01]: Support Configurable PSB and Cycle-Accurate Mode;
554 * bit[02]: Support IP Filtering, TraceStop filtering, and preservation
555 * of Intel PT MSRs across warm reset;
556 * bit[03]: Support MTC timing packet and suppression of COFI-based packets;
558 #define INTEL_PT_MINIMAL_EBX 0xf
560 * bit[00]: Tracing can be enabled with IA32_RTIT_CTL.ToPA = 1 and
561 * IA32_RTIT_OUTPUT_BASE and IA32_RTIT_OUTPUT_MASK_PTRS MSRs can be
562 * accessed;
563 * bit[01]: ToPA tables can hold any number of output entries, up to the
564 * maximum allowed by the MaskOrTableOffset field of
565 * IA32_RTIT_OUTPUT_MASK_PTRS;
566 * bit[02]: Support Single-Range Output scheme;
568 #define INTEL_PT_MINIMAL_ECX 0x7
569 /* generated packets which contain IP payloads have LIP values */
570 #define INTEL_PT_IP_LIP (1 << 31)
571 #define INTEL_PT_ADDR_RANGES_NUM 0x2 /* Number of configurable address ranges */
572 #define INTEL_PT_ADDR_RANGES_NUM_MASK 0x3
573 #define INTEL_PT_MTC_BITMAP (0x0249 << 16) /* Support ART(0,3,6,9) */
574 #define INTEL_PT_CYCLE_BITMAP 0x1fff /* Support 0,2^(0~11) */
575 #define INTEL_PT_PSB_BITMAP (0x003f << 16) /* Support 2K,4K,8K,16K,32K,64K */
577 void x86_cpu_vendor_words2str(char *dst, uint32_t vendor1,
578 uint32_t vendor2, uint32_t vendor3)
580 int i;
581 for (i = 0; i < 4; i++) {
582 dst[i] = vendor1 >> (8 * i);
583 dst[i + 4] = vendor2 >> (8 * i);
584 dst[i + 8] = vendor3 >> (8 * i);
586 dst[CPUID_VENDOR_SZ] = '\0';
589 #define I486_FEATURES (CPUID_FP87 | CPUID_VME | CPUID_PSE)
590 #define PENTIUM_FEATURES (I486_FEATURES | CPUID_DE | CPUID_TSC | \
591 CPUID_MSR | CPUID_MCE | CPUID_CX8 | CPUID_MMX | CPUID_APIC)
592 #define PENTIUM2_FEATURES (PENTIUM_FEATURES | CPUID_PAE | CPUID_SEP | \
593 CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV | CPUID_PAT | \
594 CPUID_PSE36 | CPUID_FXSR)
595 #define PENTIUM3_FEATURES (PENTIUM2_FEATURES | CPUID_SSE)
596 #define PPRO_FEATURES (CPUID_FP87 | CPUID_DE | CPUID_PSE | CPUID_TSC | \
597 CPUID_MSR | CPUID_MCE | CPUID_CX8 | CPUID_PGE | CPUID_CMOV | \
598 CPUID_PAT | CPUID_FXSR | CPUID_MMX | CPUID_SSE | CPUID_SSE2 | \
599 CPUID_PAE | CPUID_SEP | CPUID_APIC)
601 #define TCG_FEATURES (CPUID_FP87 | CPUID_PSE | CPUID_TSC | CPUID_MSR | \
602 CPUID_PAE | CPUID_MCE | CPUID_CX8 | CPUID_APIC | CPUID_SEP | \
603 CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV | CPUID_PAT | \
604 CPUID_PSE36 | CPUID_CLFLUSH | CPUID_ACPI | CPUID_MMX | \
605 CPUID_FXSR | CPUID_SSE | CPUID_SSE2 | CPUID_SS | CPUID_DE)
606 /* partly implemented:
607 CPUID_MTRR, CPUID_MCA, CPUID_CLFLUSH (needed for Win64) */
608 /* missing:
609 CPUID_VME, CPUID_DTS, CPUID_SS, CPUID_HT, CPUID_TM, CPUID_PBE */
610 #define TCG_EXT_FEATURES (CPUID_EXT_SSE3 | CPUID_EXT_PCLMULQDQ | \
611 CPUID_EXT_MONITOR | CPUID_EXT_SSSE3 | CPUID_EXT_CX16 | \
612 CPUID_EXT_SSE41 | CPUID_EXT_SSE42 | CPUID_EXT_POPCNT | \
613 CPUID_EXT_XSAVE | /* CPUID_EXT_OSXSAVE is dynamic */ \
614 CPUID_EXT_MOVBE | CPUID_EXT_AES | CPUID_EXT_HYPERVISOR | \
615 CPUID_EXT_RDRAND)
616 /* missing:
617 CPUID_EXT_DTES64, CPUID_EXT_DSCPL, CPUID_EXT_VMX, CPUID_EXT_SMX,
618 CPUID_EXT_EST, CPUID_EXT_TM2, CPUID_EXT_CID, CPUID_EXT_FMA,
619 CPUID_EXT_XTPR, CPUID_EXT_PDCM, CPUID_EXT_PCID, CPUID_EXT_DCA,
620 CPUID_EXT_X2APIC, CPUID_EXT_TSC_DEADLINE_TIMER, CPUID_EXT_AVX,
621 CPUID_EXT_F16C */
623 #ifdef TARGET_X86_64
624 #define TCG_EXT2_X86_64_FEATURES (CPUID_EXT2_SYSCALL | CPUID_EXT2_LM)
625 #else
626 #define TCG_EXT2_X86_64_FEATURES 0
627 #endif
629 #define TCG_EXT2_FEATURES ((TCG_FEATURES & CPUID_EXT2_AMD_ALIASES) | \
630 CPUID_EXT2_NX | CPUID_EXT2_MMXEXT | CPUID_EXT2_RDTSCP | \
631 CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT | CPUID_EXT2_PDPE1GB | \
632 TCG_EXT2_X86_64_FEATURES)
633 #define TCG_EXT3_FEATURES (CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM | \
634 CPUID_EXT3_CR8LEG | CPUID_EXT3_ABM | CPUID_EXT3_SSE4A)
635 #define TCG_EXT4_FEATURES 0
636 #define TCG_SVM_FEATURES (CPUID_SVM_NPT | CPUID_SVM_VGIF | \
637 CPUID_SVM_SVME_ADDR_CHK)
638 #define TCG_KVM_FEATURES 0
639 #define TCG_7_0_EBX_FEATURES (CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_SMAP | \
640 CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ADX | \
641 CPUID_7_0_EBX_PCOMMIT | CPUID_7_0_EBX_CLFLUSHOPT | \
642 CPUID_7_0_EBX_CLWB | CPUID_7_0_EBX_MPX | CPUID_7_0_EBX_FSGSBASE | \
643 CPUID_7_0_EBX_ERMS)
644 /* missing:
645 CPUID_7_0_EBX_HLE, CPUID_7_0_EBX_AVX2,
646 CPUID_7_0_EBX_INVPCID, CPUID_7_0_EBX_RTM,
647 CPUID_7_0_EBX_RDSEED */
648 #define TCG_7_0_ECX_FEATURES (CPUID_7_0_ECX_PKU | \
649 /* CPUID_7_0_ECX_OSPKE is dynamic */ \
650 CPUID_7_0_ECX_LA57 | CPUID_7_0_ECX_PKS)
651 #define TCG_7_0_EDX_FEATURES 0
652 #define TCG_7_1_EAX_FEATURES 0
653 #define TCG_APM_FEATURES 0
654 #define TCG_6_EAX_FEATURES CPUID_6_EAX_ARAT
655 #define TCG_XSAVE_FEATURES (CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XGETBV1)
656 /* missing:
657 CPUID_XSAVE_XSAVEC, CPUID_XSAVE_XSAVES */
658 #define TCG_14_0_ECX_FEATURES 0
659 #define TCG_SGX_12_0_EAX_FEATURES 0
660 #define TCG_SGX_12_0_EBX_FEATURES 0
661 #define TCG_SGX_12_1_EAX_FEATURES 0
663 FeatureWordInfo feature_word_info[FEATURE_WORDS] = {
664 [FEAT_1_EDX] = {
665 .type = CPUID_FEATURE_WORD,
666 .feat_names = {
667 "fpu", "vme", "de", "pse",
668 "tsc", "msr", "pae", "mce",
669 "cx8", "apic", NULL, "sep",
670 "mtrr", "pge", "mca", "cmov",
671 "pat", "pse36", "pn" /* Intel psn */, "clflush" /* Intel clfsh */,
672 NULL, "ds" /* Intel dts */, "acpi", "mmx",
673 "fxsr", "sse", "sse2", "ss",
674 "ht" /* Intel htt */, "tm", "ia64", "pbe",
676 .cpuid = {.eax = 1, .reg = R_EDX, },
677 .tcg_features = TCG_FEATURES,
679 [FEAT_1_ECX] = {
680 .type = CPUID_FEATURE_WORD,
681 .feat_names = {
682 "pni" /* Intel,AMD sse3 */, "pclmulqdq", "dtes64", "monitor",
683 "ds-cpl", "vmx", "smx", "est",
684 "tm2", "ssse3", "cid", NULL,
685 "fma", "cx16", "xtpr", "pdcm",
686 NULL, "pcid", "dca", "sse4.1",
687 "sse4.2", "x2apic", "movbe", "popcnt",
688 "tsc-deadline", "aes", "xsave", NULL /* osxsave */,
689 "avx", "f16c", "rdrand", "hypervisor",
691 .cpuid = { .eax = 1, .reg = R_ECX, },
692 .tcg_features = TCG_EXT_FEATURES,
694 /* Feature names that are already defined on feature_name[] but
695 * are set on CPUID[8000_0001].EDX on AMD CPUs don't have their
696 * names on feat_names below. They are copied automatically
697 * to features[FEAT_8000_0001_EDX] if and only if CPU vendor is AMD.
699 [FEAT_8000_0001_EDX] = {
700 .type = CPUID_FEATURE_WORD,
701 .feat_names = {
702 NULL /* fpu */, NULL /* vme */, NULL /* de */, NULL /* pse */,
703 NULL /* tsc */, NULL /* msr */, NULL /* pae */, NULL /* mce */,
704 NULL /* cx8 */, NULL /* apic */, NULL, "syscall",
705 NULL /* mtrr */, NULL /* pge */, NULL /* mca */, NULL /* cmov */,
706 NULL /* pat */, NULL /* pse36 */, NULL, NULL /* Linux mp */,
707 "nx", NULL, "mmxext", NULL /* mmx */,
708 NULL /* fxsr */, "fxsr-opt", "pdpe1gb", "rdtscp",
709 NULL, "lm", "3dnowext", "3dnow",
711 .cpuid = { .eax = 0x80000001, .reg = R_EDX, },
712 .tcg_features = TCG_EXT2_FEATURES,
714 [FEAT_8000_0001_ECX] = {
715 .type = CPUID_FEATURE_WORD,
716 .feat_names = {
717 "lahf-lm", "cmp-legacy", "svm", "extapic",
718 "cr8legacy", "abm", "sse4a", "misalignsse",
719 "3dnowprefetch", "osvw", "ibs", "xop",
720 "skinit", "wdt", NULL, "lwp",
721 "fma4", "tce", NULL, "nodeid-msr",
722 NULL, "tbm", "topoext", "perfctr-core",
723 "perfctr-nb", NULL, NULL, NULL,
724 NULL, NULL, NULL, NULL,
726 .cpuid = { .eax = 0x80000001, .reg = R_ECX, },
727 .tcg_features = TCG_EXT3_FEATURES,
729 * TOPOEXT is always allowed but can't be enabled blindly by
730 * "-cpu host", as it requires consistent cache topology info
731 * to be provided so it doesn't confuse guests.
733 .no_autoenable_flags = CPUID_EXT3_TOPOEXT,
735 [FEAT_C000_0001_EDX] = {
736 .type = CPUID_FEATURE_WORD,
737 .feat_names = {
738 NULL, NULL, "xstore", "xstore-en",
739 NULL, NULL, "xcrypt", "xcrypt-en",
740 "ace2", "ace2-en", "phe", "phe-en",
741 "pmm", "pmm-en", NULL, NULL,
742 NULL, NULL, NULL, NULL,
743 NULL, NULL, NULL, NULL,
744 NULL, NULL, NULL, NULL,
745 NULL, NULL, NULL, NULL,
747 .cpuid = { .eax = 0xC0000001, .reg = R_EDX, },
748 .tcg_features = TCG_EXT4_FEATURES,
750 [FEAT_KVM] = {
751 .type = CPUID_FEATURE_WORD,
752 .feat_names = {
753 "kvmclock", "kvm-nopiodelay", "kvm-mmu", "kvmclock",
754 "kvm-asyncpf", "kvm-steal-time", "kvm-pv-eoi", "kvm-pv-unhalt",
755 NULL, "kvm-pv-tlb-flush", NULL, "kvm-pv-ipi",
756 "kvm-poll-control", "kvm-pv-sched-yield", "kvm-asyncpf-int", "kvm-msi-ext-dest-id",
757 NULL, NULL, NULL, NULL,
758 NULL, NULL, NULL, NULL,
759 "kvmclock-stable-bit", NULL, NULL, NULL,
760 NULL, NULL, NULL, NULL,
762 .cpuid = { .eax = KVM_CPUID_FEATURES, .reg = R_EAX, },
763 .tcg_features = TCG_KVM_FEATURES,
765 [FEAT_KVM_HINTS] = {
766 .type = CPUID_FEATURE_WORD,
767 .feat_names = {
768 "kvm-hint-dedicated", NULL, NULL, NULL,
769 NULL, NULL, NULL, NULL,
770 NULL, NULL, NULL, NULL,
771 NULL, NULL, NULL, NULL,
772 NULL, NULL, NULL, NULL,
773 NULL, NULL, NULL, NULL,
774 NULL, NULL, NULL, NULL,
775 NULL, NULL, NULL, NULL,
777 .cpuid = { .eax = KVM_CPUID_FEATURES, .reg = R_EDX, },
778 .tcg_features = TCG_KVM_FEATURES,
780 * KVM hints aren't auto-enabled by -cpu host, they need to be
781 * explicitly enabled in the command-line.
783 .no_autoenable_flags = ~0U,
785 [FEAT_SVM] = {
786 .type = CPUID_FEATURE_WORD,
787 .feat_names = {
788 "npt", "lbrv", "svm-lock", "nrip-save",
789 "tsc-scale", "vmcb-clean", "flushbyasid", "decodeassists",
790 NULL, NULL, "pause-filter", NULL,
791 "pfthreshold", "avic", NULL, "v-vmsave-vmload",
792 "vgif", NULL, NULL, NULL,
793 NULL, NULL, NULL, NULL,
794 NULL, NULL, NULL, NULL,
795 "svme-addr-chk", NULL, NULL, NULL,
797 .cpuid = { .eax = 0x8000000A, .reg = R_EDX, },
798 .tcg_features = TCG_SVM_FEATURES,
800 [FEAT_7_0_EBX] = {
801 .type = CPUID_FEATURE_WORD,
802 .feat_names = {
803 "fsgsbase", "tsc-adjust", "sgx", "bmi1",
804 "hle", "avx2", NULL, "smep",
805 "bmi2", "erms", "invpcid", "rtm",
806 NULL, NULL, "mpx", NULL,
807 "avx512f", "avx512dq", "rdseed", "adx",
808 "smap", "avx512ifma", "pcommit", "clflushopt",
809 "clwb", "intel-pt", "avx512pf", "avx512er",
810 "avx512cd", "sha-ni", "avx512bw", "avx512vl",
812 .cpuid = {
813 .eax = 7,
814 .needs_ecx = true, .ecx = 0,
815 .reg = R_EBX,
817 .tcg_features = TCG_7_0_EBX_FEATURES,
819 [FEAT_7_0_ECX] = {
820 .type = CPUID_FEATURE_WORD,
821 .feat_names = {
822 NULL, "avx512vbmi", "umip", "pku",
823 NULL /* ospke */, "waitpkg", "avx512vbmi2", NULL,
824 "gfni", "vaes", "vpclmulqdq", "avx512vnni",
825 "avx512bitalg", NULL, "avx512-vpopcntdq", NULL,
826 "la57", NULL, NULL, NULL,
827 NULL, NULL, "rdpid", NULL,
828 "bus-lock-detect", "cldemote", NULL, "movdiri",
829 "movdir64b", NULL, "sgxlc", "pks",
831 .cpuid = {
832 .eax = 7,
833 .needs_ecx = true, .ecx = 0,
834 .reg = R_ECX,
836 .tcg_features = TCG_7_0_ECX_FEATURES,
838 [FEAT_7_0_EDX] = {
839 .type = CPUID_FEATURE_WORD,
840 .feat_names = {
841 NULL, NULL, "avx512-4vnniw", "avx512-4fmaps",
842 "fsrm", NULL, NULL, NULL,
843 "avx512-vp2intersect", NULL, "md-clear", NULL,
844 NULL, NULL, "serialize", NULL,
845 "tsx-ldtrk", NULL, NULL /* pconfig */, NULL,
846 NULL, NULL, NULL, "avx512-fp16",
847 NULL, NULL, "spec-ctrl", "stibp",
848 NULL, "arch-capabilities", "core-capability", "ssbd",
850 .cpuid = {
851 .eax = 7,
852 .needs_ecx = true, .ecx = 0,
853 .reg = R_EDX,
855 .tcg_features = TCG_7_0_EDX_FEATURES,
857 [FEAT_7_1_EAX] = {
858 .type = CPUID_FEATURE_WORD,
859 .feat_names = {
860 NULL, NULL, NULL, NULL,
861 "avx-vnni", "avx512-bf16", NULL, NULL,
862 NULL, NULL, NULL, NULL,
863 NULL, NULL, NULL, NULL,
864 NULL, NULL, NULL, NULL,
865 NULL, NULL, NULL, NULL,
866 NULL, NULL, NULL, NULL,
867 NULL, NULL, NULL, NULL,
869 .cpuid = {
870 .eax = 7,
871 .needs_ecx = true, .ecx = 1,
872 .reg = R_EAX,
874 .tcg_features = TCG_7_1_EAX_FEATURES,
876 [FEAT_8000_0007_EDX] = {
877 .type = CPUID_FEATURE_WORD,
878 .feat_names = {
879 NULL, NULL, NULL, NULL,
880 NULL, NULL, NULL, NULL,
881 "invtsc", NULL, NULL, NULL,
882 NULL, NULL, NULL, NULL,
883 NULL, NULL, NULL, NULL,
884 NULL, NULL, NULL, NULL,
885 NULL, NULL, NULL, NULL,
886 NULL, NULL, NULL, NULL,
888 .cpuid = { .eax = 0x80000007, .reg = R_EDX, },
889 .tcg_features = TCG_APM_FEATURES,
890 .unmigratable_flags = CPUID_APM_INVTSC,
892 [FEAT_8000_0008_EBX] = {
893 .type = CPUID_FEATURE_WORD,
894 .feat_names = {
895 "clzero", NULL, "xsaveerptr", NULL,
896 NULL, NULL, NULL, NULL,
897 NULL, "wbnoinvd", NULL, NULL,
898 "ibpb", NULL, "ibrs", "amd-stibp",
899 NULL, NULL, NULL, NULL,
900 NULL, NULL, NULL, NULL,
901 "amd-ssbd", "virt-ssbd", "amd-no-ssb", NULL,
902 NULL, NULL, NULL, NULL,
904 .cpuid = { .eax = 0x80000008, .reg = R_EBX, },
905 .tcg_features = 0,
906 .unmigratable_flags = 0,
908 [FEAT_XSAVE] = {
909 .type = CPUID_FEATURE_WORD,
910 .feat_names = {
911 "xsaveopt", "xsavec", "xgetbv1", "xsaves",
912 NULL, NULL, NULL, NULL,
913 NULL, NULL, NULL, NULL,
914 NULL, NULL, NULL, NULL,
915 NULL, NULL, NULL, NULL,
916 NULL, NULL, NULL, NULL,
917 NULL, NULL, NULL, NULL,
918 NULL, NULL, NULL, NULL,
920 .cpuid = {
921 .eax = 0xd,
922 .needs_ecx = true, .ecx = 1,
923 .reg = R_EAX,
925 .tcg_features = TCG_XSAVE_FEATURES,
927 [FEAT_6_EAX] = {
928 .type = CPUID_FEATURE_WORD,
929 .feat_names = {
930 NULL, NULL, "arat", NULL,
931 NULL, NULL, NULL, NULL,
932 NULL, NULL, NULL, NULL,
933 NULL, NULL, NULL, NULL,
934 NULL, NULL, NULL, NULL,
935 NULL, NULL, NULL, NULL,
936 NULL, NULL, NULL, NULL,
937 NULL, NULL, NULL, NULL,
939 .cpuid = { .eax = 6, .reg = R_EAX, },
940 .tcg_features = TCG_6_EAX_FEATURES,
942 [FEAT_XSAVE_COMP_LO] = {
943 .type = CPUID_FEATURE_WORD,
944 .cpuid = {
945 .eax = 0xD,
946 .needs_ecx = true, .ecx = 0,
947 .reg = R_EAX,
949 .tcg_features = ~0U,
950 .migratable_flags = XSTATE_FP_MASK | XSTATE_SSE_MASK |
951 XSTATE_YMM_MASK | XSTATE_BNDREGS_MASK | XSTATE_BNDCSR_MASK |
952 XSTATE_OPMASK_MASK | XSTATE_ZMM_Hi256_MASK | XSTATE_Hi16_ZMM_MASK |
953 XSTATE_PKRU_MASK,
955 [FEAT_XSAVE_COMP_HI] = {
956 .type = CPUID_FEATURE_WORD,
957 .cpuid = {
958 .eax = 0xD,
959 .needs_ecx = true, .ecx = 0,
960 .reg = R_EDX,
962 .tcg_features = ~0U,
964 /*Below are MSR exposed features*/
965 [FEAT_ARCH_CAPABILITIES] = {
966 .type = MSR_FEATURE_WORD,
967 .feat_names = {
968 "rdctl-no", "ibrs-all", "rsba", "skip-l1dfl-vmentry",
969 "ssb-no", "mds-no", "pschange-mc-no", "tsx-ctrl",
970 "taa-no", NULL, NULL, NULL,
971 NULL, NULL, NULL, NULL,
972 NULL, NULL, NULL, NULL,
973 NULL, NULL, NULL, NULL,
974 NULL, NULL, NULL, NULL,
975 NULL, NULL, NULL, NULL,
977 .msr = {
978 .index = MSR_IA32_ARCH_CAPABILITIES,
981 [FEAT_CORE_CAPABILITY] = {
982 .type = MSR_FEATURE_WORD,
983 .feat_names = {
984 NULL, NULL, NULL, NULL,
985 NULL, "split-lock-detect", NULL, NULL,
986 NULL, NULL, NULL, NULL,
987 NULL, NULL, NULL, NULL,
988 NULL, NULL, NULL, NULL,
989 NULL, NULL, NULL, NULL,
990 NULL, NULL, NULL, NULL,
991 NULL, NULL, NULL, NULL,
993 .msr = {
994 .index = MSR_IA32_CORE_CAPABILITY,
997 [FEAT_PERF_CAPABILITIES] = {
998 .type = MSR_FEATURE_WORD,
999 .feat_names = {
1000 NULL, NULL, NULL, NULL,
1001 NULL, NULL, NULL, NULL,
1002 NULL, NULL, NULL, NULL,
1003 NULL, "full-width-write", NULL, NULL,
1004 NULL, NULL, NULL, NULL,
1005 NULL, NULL, NULL, NULL,
1006 NULL, NULL, NULL, NULL,
1007 NULL, NULL, NULL, NULL,
1009 .msr = {
1010 .index = MSR_IA32_PERF_CAPABILITIES,
1014 [FEAT_VMX_PROCBASED_CTLS] = {
1015 .type = MSR_FEATURE_WORD,
1016 .feat_names = {
1017 NULL, NULL, "vmx-vintr-pending", "vmx-tsc-offset",
1018 NULL, NULL, NULL, "vmx-hlt-exit",
1019 NULL, "vmx-invlpg-exit", "vmx-mwait-exit", "vmx-rdpmc-exit",
1020 "vmx-rdtsc-exit", NULL, NULL, "vmx-cr3-load-noexit",
1021 "vmx-cr3-store-noexit", NULL, NULL, "vmx-cr8-load-exit",
1022 "vmx-cr8-store-exit", "vmx-flexpriority", "vmx-vnmi-pending", "vmx-movdr-exit",
1023 "vmx-io-exit", "vmx-io-bitmap", NULL, "vmx-mtf",
1024 "vmx-msr-bitmap", "vmx-monitor-exit", "vmx-pause-exit", "vmx-secondary-ctls",
1026 .msr = {
1027 .index = MSR_IA32_VMX_TRUE_PROCBASED_CTLS,
1031 [FEAT_VMX_SECONDARY_CTLS] = {
1032 .type = MSR_FEATURE_WORD,
1033 .feat_names = {
1034 "vmx-apicv-xapic", "vmx-ept", "vmx-desc-exit", "vmx-rdtscp-exit",
1035 "vmx-apicv-x2apic", "vmx-vpid", "vmx-wbinvd-exit", "vmx-unrestricted-guest",
1036 "vmx-apicv-register", "vmx-apicv-vid", "vmx-ple", "vmx-rdrand-exit",
1037 "vmx-invpcid-exit", "vmx-vmfunc", "vmx-shadow-vmcs", "vmx-encls-exit",
1038 "vmx-rdseed-exit", "vmx-pml", NULL, NULL,
1039 "vmx-xsaves", NULL, NULL, NULL,
1040 NULL, "vmx-tsc-scaling", NULL, NULL,
1041 NULL, NULL, NULL, NULL,
1043 .msr = {
1044 .index = MSR_IA32_VMX_PROCBASED_CTLS2,
1048 [FEAT_VMX_PINBASED_CTLS] = {
1049 .type = MSR_FEATURE_WORD,
1050 .feat_names = {
1051 "vmx-intr-exit", NULL, NULL, "vmx-nmi-exit",
1052 NULL, "vmx-vnmi", "vmx-preemption-timer", "vmx-posted-intr",
1053 NULL, NULL, NULL, NULL,
1054 NULL, NULL, NULL, NULL,
1055 NULL, NULL, NULL, NULL,
1056 NULL, NULL, NULL, NULL,
1057 NULL, NULL, NULL, NULL,
1058 NULL, NULL, NULL, NULL,
1060 .msr = {
1061 .index = MSR_IA32_VMX_TRUE_PINBASED_CTLS,
1065 [FEAT_VMX_EXIT_CTLS] = {
1066 .type = MSR_FEATURE_WORD,
1068 * VMX_VM_EXIT_HOST_ADDR_SPACE_SIZE is copied from
1069 * the LM CPUID bit.
1071 .feat_names = {
1072 NULL, NULL, "vmx-exit-nosave-debugctl", NULL,
1073 NULL, NULL, NULL, NULL,
1074 NULL, NULL /* vmx-exit-host-addr-space-size */, NULL, NULL,
1075 "vmx-exit-load-perf-global-ctrl", NULL, NULL, "vmx-exit-ack-intr",
1076 NULL, NULL, "vmx-exit-save-pat", "vmx-exit-load-pat",
1077 "vmx-exit-save-efer", "vmx-exit-load-efer",
1078 "vmx-exit-save-preemption-timer", "vmx-exit-clear-bndcfgs",
1079 NULL, "vmx-exit-clear-rtit-ctl", NULL, NULL,
1080 NULL, "vmx-exit-load-pkrs", NULL, NULL,
1082 .msr = {
1083 .index = MSR_IA32_VMX_TRUE_EXIT_CTLS,
1087 [FEAT_VMX_ENTRY_CTLS] = {
1088 .type = MSR_FEATURE_WORD,
1089 .feat_names = {
1090 NULL, NULL, "vmx-entry-noload-debugctl", NULL,
1091 NULL, NULL, NULL, NULL,
1092 NULL, "vmx-entry-ia32e-mode", NULL, NULL,
1093 NULL, "vmx-entry-load-perf-global-ctrl", "vmx-entry-load-pat", "vmx-entry-load-efer",
1094 "vmx-entry-load-bndcfgs", NULL, "vmx-entry-load-rtit-ctl", NULL,
1095 NULL, NULL, "vmx-entry-load-pkrs", NULL,
1096 NULL, NULL, NULL, NULL,
1097 NULL, NULL, NULL, NULL,
1099 .msr = {
1100 .index = MSR_IA32_VMX_TRUE_ENTRY_CTLS,
1104 [FEAT_VMX_MISC] = {
1105 .type = MSR_FEATURE_WORD,
1106 .feat_names = {
1107 NULL, NULL, NULL, NULL,
1108 NULL, "vmx-store-lma", "vmx-activity-hlt", "vmx-activity-shutdown",
1109 "vmx-activity-wait-sipi", NULL, NULL, NULL,
1110 NULL, NULL, NULL, NULL,
1111 NULL, NULL, NULL, NULL,
1112 NULL, NULL, NULL, NULL,
1113 NULL, NULL, NULL, NULL,
1114 NULL, "vmx-vmwrite-vmexit-fields", "vmx-zero-len-inject", NULL,
1116 .msr = {
1117 .index = MSR_IA32_VMX_MISC,
1121 [FEAT_VMX_EPT_VPID_CAPS] = {
1122 .type = MSR_FEATURE_WORD,
1123 .feat_names = {
1124 "vmx-ept-execonly", NULL, NULL, NULL,
1125 NULL, NULL, "vmx-page-walk-4", "vmx-page-walk-5",
1126 NULL, NULL, NULL, NULL,
1127 NULL, NULL, NULL, NULL,
1128 "vmx-ept-2mb", "vmx-ept-1gb", NULL, NULL,
1129 "vmx-invept", "vmx-eptad", "vmx-ept-advanced-exitinfo", NULL,
1130 NULL, "vmx-invept-single-context", "vmx-invept-all-context", NULL,
1131 NULL, NULL, NULL, NULL,
1132 "vmx-invvpid", NULL, NULL, NULL,
1133 NULL, NULL, NULL, NULL,
1134 "vmx-invvpid-single-addr", "vmx-invept-single-context",
1135 "vmx-invvpid-all-context", "vmx-invept-single-context-noglobals",
1136 NULL, NULL, NULL, NULL,
1137 NULL, NULL, NULL, NULL,
1138 NULL, NULL, NULL, NULL,
1139 NULL, NULL, NULL, NULL,
1140 NULL, NULL, NULL, NULL,
1142 .msr = {
1143 .index = MSR_IA32_VMX_EPT_VPID_CAP,
1147 [FEAT_VMX_BASIC] = {
1148 .type = MSR_FEATURE_WORD,
1149 .feat_names = {
1150 [54] = "vmx-ins-outs",
1151 [55] = "vmx-true-ctls",
1153 .msr = {
1154 .index = MSR_IA32_VMX_BASIC,
1156 /* Just to be safe - we don't support setting the MSEG version field. */
1157 .no_autoenable_flags = MSR_VMX_BASIC_DUAL_MONITOR,
1160 [FEAT_VMX_VMFUNC] = {
1161 .type = MSR_FEATURE_WORD,
1162 .feat_names = {
1163 [0] = "vmx-eptp-switching",
1165 .msr = {
1166 .index = MSR_IA32_VMX_VMFUNC,
1170 [FEAT_14_0_ECX] = {
1171 .type = CPUID_FEATURE_WORD,
1172 .feat_names = {
1173 NULL, NULL, NULL, NULL,
1174 NULL, NULL, NULL, NULL,
1175 NULL, NULL, NULL, NULL,
1176 NULL, NULL, NULL, NULL,
1177 NULL, NULL, NULL, NULL,
1178 NULL, NULL, NULL, NULL,
1179 NULL, NULL, NULL, NULL,
1180 NULL, NULL, NULL, "intel-pt-lip",
1182 .cpuid = {
1183 .eax = 0x14,
1184 .needs_ecx = true, .ecx = 0,
1185 .reg = R_ECX,
1187 .tcg_features = TCG_14_0_ECX_FEATURES,
1190 [FEAT_SGX_12_0_EAX] = {
1191 .type = CPUID_FEATURE_WORD,
1192 .feat_names = {
1193 "sgx1", "sgx2", NULL, NULL,
1194 NULL, NULL, NULL, NULL,
1195 NULL, NULL, NULL, NULL,
1196 NULL, NULL, NULL, NULL,
1197 NULL, NULL, NULL, NULL,
1198 NULL, NULL, NULL, NULL,
1199 NULL, NULL, NULL, NULL,
1200 NULL, NULL, NULL, NULL,
1202 .cpuid = {
1203 .eax = 0x12,
1204 .needs_ecx = true, .ecx = 0,
1205 .reg = R_EAX,
1207 .tcg_features = TCG_SGX_12_0_EAX_FEATURES,
1210 [FEAT_SGX_12_0_EBX] = {
1211 .type = CPUID_FEATURE_WORD,
1212 .feat_names = {
1213 "sgx-exinfo" , NULL, NULL, NULL,
1214 NULL, NULL, NULL, NULL,
1215 NULL, NULL, NULL, NULL,
1216 NULL, NULL, NULL, NULL,
1217 NULL, NULL, NULL, NULL,
1218 NULL, NULL, NULL, NULL,
1219 NULL, NULL, NULL, NULL,
1220 NULL, NULL, NULL, NULL,
1222 .cpuid = {
1223 .eax = 0x12,
1224 .needs_ecx = true, .ecx = 0,
1225 .reg = R_EBX,
1227 .tcg_features = TCG_SGX_12_0_EBX_FEATURES,
1230 [FEAT_SGX_12_1_EAX] = {
1231 .type = CPUID_FEATURE_WORD,
1232 .feat_names = {
1233 NULL, "sgx-debug", "sgx-mode64", NULL,
1234 "sgx-provisionkey", "sgx-tokenkey", NULL, "sgx-kss",
1235 NULL, NULL, NULL, NULL,
1236 NULL, NULL, NULL, NULL,
1237 NULL, NULL, NULL, NULL,
1238 NULL, NULL, NULL, NULL,
1239 NULL, NULL, NULL, NULL,
1240 NULL, NULL, NULL, NULL,
1242 .cpuid = {
1243 .eax = 0x12,
1244 .needs_ecx = true, .ecx = 1,
1245 .reg = R_EAX,
1247 .tcg_features = TCG_SGX_12_1_EAX_FEATURES,
1251 typedef struct FeatureMask {
1252 FeatureWord index;
1253 uint64_t mask;
1254 } FeatureMask;
1256 typedef struct FeatureDep {
1257 FeatureMask from, to;
1258 } FeatureDep;
1260 static FeatureDep feature_dependencies[] = {
1262 .from = { FEAT_7_0_EDX, CPUID_7_0_EDX_ARCH_CAPABILITIES },
1263 .to = { FEAT_ARCH_CAPABILITIES, ~0ull },
1266 .from = { FEAT_7_0_EDX, CPUID_7_0_EDX_CORE_CAPABILITY },
1267 .to = { FEAT_CORE_CAPABILITY, ~0ull },
1270 .from = { FEAT_1_ECX, CPUID_EXT_PDCM },
1271 .to = { FEAT_PERF_CAPABILITIES, ~0ull },
1274 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1275 .to = { FEAT_VMX_PROCBASED_CTLS, ~0ull },
1278 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1279 .to = { FEAT_VMX_PINBASED_CTLS, ~0ull },
1282 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1283 .to = { FEAT_VMX_EXIT_CTLS, ~0ull },
1286 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1287 .to = { FEAT_VMX_ENTRY_CTLS, ~0ull },
1290 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1291 .to = { FEAT_VMX_MISC, ~0ull },
1294 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1295 .to = { FEAT_VMX_BASIC, ~0ull },
1298 .from = { FEAT_8000_0001_EDX, CPUID_EXT2_LM },
1299 .to = { FEAT_VMX_ENTRY_CTLS, VMX_VM_ENTRY_IA32E_MODE },
1302 .from = { FEAT_VMX_PROCBASED_CTLS, VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS },
1303 .to = { FEAT_VMX_SECONDARY_CTLS, ~0ull },
1306 .from = { FEAT_XSAVE, CPUID_XSAVE_XSAVES },
1307 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_XSAVES },
1310 .from = { FEAT_1_ECX, CPUID_EXT_RDRAND },
1311 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_RDRAND_EXITING },
1314 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_INVPCID },
1315 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_INVPCID },
1318 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_RDSEED },
1319 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_RDSEED_EXITING },
1322 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_INTEL_PT },
1323 .to = { FEAT_14_0_ECX, ~0ull },
1326 .from = { FEAT_8000_0001_EDX, CPUID_EXT2_RDTSCP },
1327 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_RDTSCP },
1330 .from = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_EPT },
1331 .to = { FEAT_VMX_EPT_VPID_CAPS, 0xffffffffull },
1334 .from = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_EPT },
1335 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST },
1338 .from = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_VPID },
1339 .to = { FEAT_VMX_EPT_VPID_CAPS, 0xffffffffull << 32 },
1342 .from = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_VMFUNC },
1343 .to = { FEAT_VMX_VMFUNC, ~0ull },
1346 .from = { FEAT_8000_0001_ECX, CPUID_EXT3_SVM },
1347 .to = { FEAT_SVM, ~0ull },
1351 typedef struct X86RegisterInfo32 {
1352 /* Name of register */
1353 const char *name;
1354 /* QAPI enum value register */
1355 X86CPURegister32 qapi_enum;
1356 } X86RegisterInfo32;
1358 #define REGISTER(reg) \
1359 [R_##reg] = { .name = #reg, .qapi_enum = X86_CPU_REGISTER32_##reg }
1360 static const X86RegisterInfo32 x86_reg_info_32[CPU_NB_REGS32] = {
1361 REGISTER(EAX),
1362 REGISTER(ECX),
1363 REGISTER(EDX),
1364 REGISTER(EBX),
1365 REGISTER(ESP),
1366 REGISTER(EBP),
1367 REGISTER(ESI),
1368 REGISTER(EDI),
1370 #undef REGISTER
1372 ExtSaveArea x86_ext_save_areas[XSAVE_STATE_AREA_COUNT] = {
1373 [XSTATE_FP_BIT] = {
1374 /* x87 FP state component is always enabled if XSAVE is supported */
1375 .feature = FEAT_1_ECX, .bits = CPUID_EXT_XSAVE,
1376 .size = sizeof(X86LegacyXSaveArea) + sizeof(X86XSaveHeader),
1378 [XSTATE_SSE_BIT] = {
1379 /* SSE state component is always enabled if XSAVE is supported */
1380 .feature = FEAT_1_ECX, .bits = CPUID_EXT_XSAVE,
1381 .size = sizeof(X86LegacyXSaveArea) + sizeof(X86XSaveHeader),
1383 [XSTATE_YMM_BIT] =
1384 { .feature = FEAT_1_ECX, .bits = CPUID_EXT_AVX,
1385 .size = sizeof(XSaveAVX) },
1386 [XSTATE_BNDREGS_BIT] =
1387 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_MPX,
1388 .size = sizeof(XSaveBNDREG) },
1389 [XSTATE_BNDCSR_BIT] =
1390 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_MPX,
1391 .size = sizeof(XSaveBNDCSR) },
1392 [XSTATE_OPMASK_BIT] =
1393 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_AVX512F,
1394 .size = sizeof(XSaveOpmask) },
1395 [XSTATE_ZMM_Hi256_BIT] =
1396 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_AVX512F,
1397 .size = sizeof(XSaveZMM_Hi256) },
1398 [XSTATE_Hi16_ZMM_BIT] =
1399 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_AVX512F,
1400 .size = sizeof(XSaveHi16_ZMM) },
1401 [XSTATE_PKRU_BIT] =
1402 { .feature = FEAT_7_0_ECX, .bits = CPUID_7_0_ECX_PKU,
1403 .size = sizeof(XSavePKRU) },
1406 static uint32_t xsave_area_size(uint64_t mask)
1408 int i;
1409 uint64_t ret = 0;
1411 for (i = 0; i < ARRAY_SIZE(x86_ext_save_areas); i++) {
1412 const ExtSaveArea *esa = &x86_ext_save_areas[i];
1413 if ((mask >> i) & 1) {
1414 ret = MAX(ret, esa->offset + esa->size);
1417 return ret;
1420 static inline bool accel_uses_host_cpuid(void)
1422 return kvm_enabled() || hvf_enabled();
1425 static inline uint64_t x86_cpu_xsave_components(X86CPU *cpu)
1427 return ((uint64_t)cpu->env.features[FEAT_XSAVE_COMP_HI]) << 32 |
1428 cpu->env.features[FEAT_XSAVE_COMP_LO];
1431 /* Return name of 32-bit register, from a R_* constant */
1432 static const char *get_register_name_32(unsigned int reg)
1434 if (reg >= CPU_NB_REGS32) {
1435 return NULL;
1437 return x86_reg_info_32[reg].name;
1441 * Returns the set of feature flags that are supported and migratable by
1442 * QEMU, for a given FeatureWord.
1444 static uint64_t x86_cpu_get_migratable_flags(FeatureWord w)
1446 FeatureWordInfo *wi = &feature_word_info[w];
1447 uint64_t r = 0;
1448 int i;
1450 for (i = 0; i < 64; i++) {
1451 uint64_t f = 1ULL << i;
1453 /* If the feature name is known, it is implicitly considered migratable,
1454 * unless it is explicitly set in unmigratable_flags */
1455 if ((wi->migratable_flags & f) ||
1456 (wi->feat_names[i] && !(wi->unmigratable_flags & f))) {
1457 r |= f;
1460 return r;
1463 void host_cpuid(uint32_t function, uint32_t count,
1464 uint32_t *eax, uint32_t *ebx, uint32_t *ecx, uint32_t *edx)
1466 uint32_t vec[4];
1468 #ifdef __x86_64__
1469 asm volatile("cpuid"
1470 : "=a"(vec[0]), "=b"(vec[1]),
1471 "=c"(vec[2]), "=d"(vec[3])
1472 : "0"(function), "c"(count) : "cc");
1473 #elif defined(__i386__)
1474 asm volatile("pusha \n\t"
1475 "cpuid \n\t"
1476 "mov %%eax, 0(%2) \n\t"
1477 "mov %%ebx, 4(%2) \n\t"
1478 "mov %%ecx, 8(%2) \n\t"
1479 "mov %%edx, 12(%2) \n\t"
1480 "popa"
1481 : : "a"(function), "c"(count), "S"(vec)
1482 : "memory", "cc");
1483 #else
1484 abort();
1485 #endif
1487 if (eax)
1488 *eax = vec[0];
1489 if (ebx)
1490 *ebx = vec[1];
1491 if (ecx)
1492 *ecx = vec[2];
1493 if (edx)
1494 *edx = vec[3];
1497 /* CPU class name definitions: */
1499 /* Return type name for a given CPU model name
1500 * Caller is responsible for freeing the returned string.
1502 static char *x86_cpu_type_name(const char *model_name)
1504 return g_strdup_printf(X86_CPU_TYPE_NAME("%s"), model_name);
1507 static ObjectClass *x86_cpu_class_by_name(const char *cpu_model)
1509 g_autofree char *typename = x86_cpu_type_name(cpu_model);
1510 return object_class_by_name(typename);
1513 static char *x86_cpu_class_get_model_name(X86CPUClass *cc)
1515 const char *class_name = object_class_get_name(OBJECT_CLASS(cc));
1516 assert(g_str_has_suffix(class_name, X86_CPU_TYPE_SUFFIX));
1517 return g_strndup(class_name,
1518 strlen(class_name) - strlen(X86_CPU_TYPE_SUFFIX));
1521 typedef struct X86CPUVersionDefinition {
1522 X86CPUVersion version;
1523 const char *alias;
1524 const char *note;
1525 PropValue *props;
1526 } X86CPUVersionDefinition;
1528 /* Base definition for a CPU model */
1529 typedef struct X86CPUDefinition {
1530 const char *name;
1531 uint32_t level;
1532 uint32_t xlevel;
1533 /* vendor is zero-terminated, 12 character ASCII string */
1534 char vendor[CPUID_VENDOR_SZ + 1];
1535 int family;
1536 int model;
1537 int stepping;
1538 FeatureWordArray features;
1539 const char *model_id;
1540 const CPUCaches *const cache_info;
1542 * Definitions for alternative versions of CPU model.
1543 * List is terminated by item with version == 0.
1544 * If NULL, version 1 will be registered automatically.
1546 const X86CPUVersionDefinition *versions;
1547 const char *deprecation_note;
1548 } X86CPUDefinition;
1550 /* Reference to a specific CPU model version */
1551 struct X86CPUModel {
1552 /* Base CPU definition */
1553 const X86CPUDefinition *cpudef;
1554 /* CPU model version */
1555 X86CPUVersion version;
1556 const char *note;
1558 * If true, this is an alias CPU model.
1559 * This matters only for "-cpu help" and query-cpu-definitions
1561 bool is_alias;
1564 /* Get full model name for CPU version */
1565 static char *x86_cpu_versioned_model_name(const X86CPUDefinition *cpudef,
1566 X86CPUVersion version)
1568 assert(version > 0);
1569 return g_strdup_printf("%s-v%d", cpudef->name, (int)version);
1572 static const X86CPUVersionDefinition *
1573 x86_cpu_def_get_versions(const X86CPUDefinition *def)
1575 /* When X86CPUDefinition::versions is NULL, we register only v1 */
1576 static const X86CPUVersionDefinition default_version_list[] = {
1577 { 1 },
1578 { /* end of list */ }
1581 return def->versions ?: default_version_list;
1584 static const CPUCaches epyc_cache_info = {
1585 .l1d_cache = &(CPUCacheInfo) {
1586 .type = DATA_CACHE,
1587 .level = 1,
1588 .size = 32 * KiB,
1589 .line_size = 64,
1590 .associativity = 8,
1591 .partitions = 1,
1592 .sets = 64,
1593 .lines_per_tag = 1,
1594 .self_init = 1,
1595 .no_invd_sharing = true,
1597 .l1i_cache = &(CPUCacheInfo) {
1598 .type = INSTRUCTION_CACHE,
1599 .level = 1,
1600 .size = 64 * KiB,
1601 .line_size = 64,
1602 .associativity = 4,
1603 .partitions = 1,
1604 .sets = 256,
1605 .lines_per_tag = 1,
1606 .self_init = 1,
1607 .no_invd_sharing = true,
1609 .l2_cache = &(CPUCacheInfo) {
1610 .type = UNIFIED_CACHE,
1611 .level = 2,
1612 .size = 512 * KiB,
1613 .line_size = 64,
1614 .associativity = 8,
1615 .partitions = 1,
1616 .sets = 1024,
1617 .lines_per_tag = 1,
1619 .l3_cache = &(CPUCacheInfo) {
1620 .type = UNIFIED_CACHE,
1621 .level = 3,
1622 .size = 8 * MiB,
1623 .line_size = 64,
1624 .associativity = 16,
1625 .partitions = 1,
1626 .sets = 8192,
1627 .lines_per_tag = 1,
1628 .self_init = true,
1629 .inclusive = true,
1630 .complex_indexing = true,
1634 static const CPUCaches epyc_rome_cache_info = {
1635 .l1d_cache = &(CPUCacheInfo) {
1636 .type = DATA_CACHE,
1637 .level = 1,
1638 .size = 32 * KiB,
1639 .line_size = 64,
1640 .associativity = 8,
1641 .partitions = 1,
1642 .sets = 64,
1643 .lines_per_tag = 1,
1644 .self_init = 1,
1645 .no_invd_sharing = true,
1647 .l1i_cache = &(CPUCacheInfo) {
1648 .type = INSTRUCTION_CACHE,
1649 .level = 1,
1650 .size = 32 * KiB,
1651 .line_size = 64,
1652 .associativity = 8,
1653 .partitions = 1,
1654 .sets = 64,
1655 .lines_per_tag = 1,
1656 .self_init = 1,
1657 .no_invd_sharing = true,
1659 .l2_cache = &(CPUCacheInfo) {
1660 .type = UNIFIED_CACHE,
1661 .level = 2,
1662 .size = 512 * KiB,
1663 .line_size = 64,
1664 .associativity = 8,
1665 .partitions = 1,
1666 .sets = 1024,
1667 .lines_per_tag = 1,
1669 .l3_cache = &(CPUCacheInfo) {
1670 .type = UNIFIED_CACHE,
1671 .level = 3,
1672 .size = 16 * MiB,
1673 .line_size = 64,
1674 .associativity = 16,
1675 .partitions = 1,
1676 .sets = 16384,
1677 .lines_per_tag = 1,
1678 .self_init = true,
1679 .inclusive = true,
1680 .complex_indexing = true,
1684 static const CPUCaches epyc_milan_cache_info = {
1685 .l1d_cache = &(CPUCacheInfo) {
1686 .type = DATA_CACHE,
1687 .level = 1,
1688 .size = 32 * KiB,
1689 .line_size = 64,
1690 .associativity = 8,
1691 .partitions = 1,
1692 .sets = 64,
1693 .lines_per_tag = 1,
1694 .self_init = 1,
1695 .no_invd_sharing = true,
1697 .l1i_cache = &(CPUCacheInfo) {
1698 .type = INSTRUCTION_CACHE,
1699 .level = 1,
1700 .size = 32 * KiB,
1701 .line_size = 64,
1702 .associativity = 8,
1703 .partitions = 1,
1704 .sets = 64,
1705 .lines_per_tag = 1,
1706 .self_init = 1,
1707 .no_invd_sharing = true,
1709 .l2_cache = &(CPUCacheInfo) {
1710 .type = UNIFIED_CACHE,
1711 .level = 2,
1712 .size = 512 * KiB,
1713 .line_size = 64,
1714 .associativity = 8,
1715 .partitions = 1,
1716 .sets = 1024,
1717 .lines_per_tag = 1,
1719 .l3_cache = &(CPUCacheInfo) {
1720 .type = UNIFIED_CACHE,
1721 .level = 3,
1722 .size = 32 * MiB,
1723 .line_size = 64,
1724 .associativity = 16,
1725 .partitions = 1,
1726 .sets = 32768,
1727 .lines_per_tag = 1,
1728 .self_init = true,
1729 .inclusive = true,
1730 .complex_indexing = true,
1734 /* The following VMX features are not supported by KVM and are left out in the
1735 * CPU definitions:
1737 * Dual-monitor support (all processors)
1738 * Entry to SMM
1739 * Deactivate dual-monitor treatment
1740 * Number of CR3-target values
1741 * Shutdown activity state
1742 * Wait-for-SIPI activity state
1743 * PAUSE-loop exiting (Westmere and newer)
1744 * EPT-violation #VE (Broadwell and newer)
1745 * Inject event with insn length=0 (Skylake and newer)
1746 * Conceal non-root operation from PT
1747 * Conceal VM exits from PT
1748 * Conceal VM entries from PT
1749 * Enable ENCLS exiting
1750 * Mode-based execute control (XS/XU)
1751 s TSC scaling (Skylake Server and newer)
1752 * GPA translation for PT (IceLake and newer)
1753 * User wait and pause
1754 * ENCLV exiting
1755 * Load IA32_RTIT_CTL
1756 * Clear IA32_RTIT_CTL
1757 * Advanced VM-exit information for EPT violations
1758 * Sub-page write permissions
1759 * PT in VMX operation
1762 static const X86CPUDefinition builtin_x86_defs[] = {
1764 .name = "qemu64",
1765 .level = 0xd,
1766 .vendor = CPUID_VENDOR_AMD,
1767 .family = 15,
1768 .model = 107,
1769 .stepping = 1,
1770 .features[FEAT_1_EDX] =
1771 PPRO_FEATURES |
1772 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
1773 CPUID_PSE36,
1774 .features[FEAT_1_ECX] =
1775 CPUID_EXT_SSE3 | CPUID_EXT_CX16,
1776 .features[FEAT_8000_0001_EDX] =
1777 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
1778 .features[FEAT_8000_0001_ECX] =
1779 CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM,
1780 .xlevel = 0x8000000A,
1781 .model_id = "QEMU Virtual CPU version " QEMU_HW_VERSION,
1784 .name = "phenom",
1785 .level = 5,
1786 .vendor = CPUID_VENDOR_AMD,
1787 .family = 16,
1788 .model = 2,
1789 .stepping = 3,
1790 /* Missing: CPUID_HT */
1791 .features[FEAT_1_EDX] =
1792 PPRO_FEATURES |
1793 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
1794 CPUID_PSE36 | CPUID_VME,
1795 .features[FEAT_1_ECX] =
1796 CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_CX16 |
1797 CPUID_EXT_POPCNT,
1798 .features[FEAT_8000_0001_EDX] =
1799 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX |
1800 CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT | CPUID_EXT2_MMXEXT |
1801 CPUID_EXT2_FFXSR | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP,
1802 /* Missing: CPUID_EXT3_CMP_LEG, CPUID_EXT3_EXTAPIC,
1803 CPUID_EXT3_CR8LEG,
1804 CPUID_EXT3_MISALIGNSSE, CPUID_EXT3_3DNOWPREFETCH,
1805 CPUID_EXT3_OSVW, CPUID_EXT3_IBS */
1806 .features[FEAT_8000_0001_ECX] =
1807 CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM |
1808 CPUID_EXT3_ABM | CPUID_EXT3_SSE4A,
1809 /* Missing: CPUID_SVM_LBRV */
1810 .features[FEAT_SVM] =
1811 CPUID_SVM_NPT,
1812 .xlevel = 0x8000001A,
1813 .model_id = "AMD Phenom(tm) 9550 Quad-Core Processor"
1816 .name = "core2duo",
1817 .level = 10,
1818 .vendor = CPUID_VENDOR_INTEL,
1819 .family = 6,
1820 .model = 15,
1821 .stepping = 11,
1822 /* Missing: CPUID_DTS, CPUID_HT, CPUID_TM, CPUID_PBE */
1823 .features[FEAT_1_EDX] =
1824 PPRO_FEATURES |
1825 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
1826 CPUID_PSE36 | CPUID_VME | CPUID_ACPI | CPUID_SS,
1827 /* Missing: CPUID_EXT_DTES64, CPUID_EXT_DSCPL, CPUID_EXT_EST,
1828 * CPUID_EXT_TM2, CPUID_EXT_XTPR, CPUID_EXT_PDCM, CPUID_EXT_VMX */
1829 .features[FEAT_1_ECX] =
1830 CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_SSSE3 |
1831 CPUID_EXT_CX16,
1832 .features[FEAT_8000_0001_EDX] =
1833 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
1834 .features[FEAT_8000_0001_ECX] =
1835 CPUID_EXT3_LAHF_LM,
1836 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS,
1837 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
1838 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
1839 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
1840 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
1841 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS,
1842 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
1843 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
1844 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
1845 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
1846 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
1847 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
1848 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
1849 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
1850 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
1851 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
1852 .features[FEAT_VMX_SECONDARY_CTLS] =
1853 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES,
1854 .xlevel = 0x80000008,
1855 .model_id = "Intel(R) Core(TM)2 Duo CPU T7700 @ 2.40GHz",
1858 .name = "kvm64",
1859 .level = 0xd,
1860 .vendor = CPUID_VENDOR_INTEL,
1861 .family = 15,
1862 .model = 6,
1863 .stepping = 1,
1864 /* Missing: CPUID_HT */
1865 .features[FEAT_1_EDX] =
1866 PPRO_FEATURES | CPUID_VME |
1867 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
1868 CPUID_PSE36,
1869 /* Missing: CPUID_EXT_POPCNT, CPUID_EXT_MONITOR */
1870 .features[FEAT_1_ECX] =
1871 CPUID_EXT_SSE3 | CPUID_EXT_CX16,
1872 /* Missing: CPUID_EXT2_PDPE1GB, CPUID_EXT2_RDTSCP */
1873 .features[FEAT_8000_0001_EDX] =
1874 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
1875 /* Missing: CPUID_EXT3_LAHF_LM, CPUID_EXT3_CMP_LEG, CPUID_EXT3_EXTAPIC,
1876 CPUID_EXT3_CR8LEG, CPUID_EXT3_ABM, CPUID_EXT3_SSE4A,
1877 CPUID_EXT3_MISALIGNSSE, CPUID_EXT3_3DNOWPREFETCH,
1878 CPUID_EXT3_OSVW, CPUID_EXT3_IBS, CPUID_EXT3_SVM */
1879 .features[FEAT_8000_0001_ECX] =
1881 /* VMX features from Cedar Mill/Prescott */
1882 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
1883 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
1884 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
1885 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
1886 VMX_PIN_BASED_NMI_EXITING,
1887 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
1888 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
1889 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
1890 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
1891 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
1892 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
1893 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
1894 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING,
1895 .xlevel = 0x80000008,
1896 .model_id = "Common KVM processor"
1899 .name = "qemu32",
1900 .level = 4,
1901 .vendor = CPUID_VENDOR_INTEL,
1902 .family = 6,
1903 .model = 6,
1904 .stepping = 3,
1905 .features[FEAT_1_EDX] =
1906 PPRO_FEATURES,
1907 .features[FEAT_1_ECX] =
1908 CPUID_EXT_SSE3,
1909 .xlevel = 0x80000004,
1910 .model_id = "QEMU Virtual CPU version " QEMU_HW_VERSION,
1913 .name = "kvm32",
1914 .level = 5,
1915 .vendor = CPUID_VENDOR_INTEL,
1916 .family = 15,
1917 .model = 6,
1918 .stepping = 1,
1919 .features[FEAT_1_EDX] =
1920 PPRO_FEATURES | CPUID_VME |
1921 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_PSE36,
1922 .features[FEAT_1_ECX] =
1923 CPUID_EXT_SSE3,
1924 .features[FEAT_8000_0001_ECX] =
1926 /* VMX features from Yonah */
1927 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
1928 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
1929 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
1930 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
1931 VMX_PIN_BASED_NMI_EXITING,
1932 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
1933 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
1934 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
1935 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
1936 VMX_CPU_BASED_MOV_DR_EXITING | VMX_CPU_BASED_UNCOND_IO_EXITING |
1937 VMX_CPU_BASED_USE_IO_BITMAPS | VMX_CPU_BASED_MONITOR_EXITING |
1938 VMX_CPU_BASED_PAUSE_EXITING | VMX_CPU_BASED_USE_MSR_BITMAPS,
1939 .xlevel = 0x80000008,
1940 .model_id = "Common 32-bit KVM processor"
1943 .name = "coreduo",
1944 .level = 10,
1945 .vendor = CPUID_VENDOR_INTEL,
1946 .family = 6,
1947 .model = 14,
1948 .stepping = 8,
1949 /* Missing: CPUID_DTS, CPUID_HT, CPUID_TM, CPUID_PBE */
1950 .features[FEAT_1_EDX] =
1951 PPRO_FEATURES | CPUID_VME |
1952 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_ACPI |
1953 CPUID_SS,
1954 /* Missing: CPUID_EXT_EST, CPUID_EXT_TM2 , CPUID_EXT_XTPR,
1955 * CPUID_EXT_PDCM, CPUID_EXT_VMX */
1956 .features[FEAT_1_ECX] =
1957 CPUID_EXT_SSE3 | CPUID_EXT_MONITOR,
1958 .features[FEAT_8000_0001_EDX] =
1959 CPUID_EXT2_NX,
1960 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
1961 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
1962 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
1963 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
1964 VMX_PIN_BASED_NMI_EXITING,
1965 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
1966 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
1967 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
1968 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
1969 VMX_CPU_BASED_MOV_DR_EXITING | VMX_CPU_BASED_UNCOND_IO_EXITING |
1970 VMX_CPU_BASED_USE_IO_BITMAPS | VMX_CPU_BASED_MONITOR_EXITING |
1971 VMX_CPU_BASED_PAUSE_EXITING | VMX_CPU_BASED_USE_MSR_BITMAPS,
1972 .xlevel = 0x80000008,
1973 .model_id = "Genuine Intel(R) CPU T2600 @ 2.16GHz",
1976 .name = "486",
1977 .level = 1,
1978 .vendor = CPUID_VENDOR_INTEL,
1979 .family = 4,
1980 .model = 8,
1981 .stepping = 0,
1982 .features[FEAT_1_EDX] =
1983 I486_FEATURES,
1984 .xlevel = 0,
1985 .model_id = "",
1988 .name = "pentium",
1989 .level = 1,
1990 .vendor = CPUID_VENDOR_INTEL,
1991 .family = 5,
1992 .model = 4,
1993 .stepping = 3,
1994 .features[FEAT_1_EDX] =
1995 PENTIUM_FEATURES,
1996 .xlevel = 0,
1997 .model_id = "",
2000 .name = "pentium2",
2001 .level = 2,
2002 .vendor = CPUID_VENDOR_INTEL,
2003 .family = 6,
2004 .model = 5,
2005 .stepping = 2,
2006 .features[FEAT_1_EDX] =
2007 PENTIUM2_FEATURES,
2008 .xlevel = 0,
2009 .model_id = "",
2012 .name = "pentium3",
2013 .level = 3,
2014 .vendor = CPUID_VENDOR_INTEL,
2015 .family = 6,
2016 .model = 7,
2017 .stepping = 3,
2018 .features[FEAT_1_EDX] =
2019 PENTIUM3_FEATURES,
2020 .xlevel = 0,
2021 .model_id = "",
2024 .name = "athlon",
2025 .level = 2,
2026 .vendor = CPUID_VENDOR_AMD,
2027 .family = 6,
2028 .model = 2,
2029 .stepping = 3,
2030 .features[FEAT_1_EDX] =
2031 PPRO_FEATURES | CPUID_PSE36 | CPUID_VME | CPUID_MTRR |
2032 CPUID_MCA,
2033 .features[FEAT_8000_0001_EDX] =
2034 CPUID_EXT2_MMXEXT | CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT,
2035 .xlevel = 0x80000008,
2036 .model_id = "QEMU Virtual CPU version " QEMU_HW_VERSION,
2039 .name = "n270",
2040 .level = 10,
2041 .vendor = CPUID_VENDOR_INTEL,
2042 .family = 6,
2043 .model = 28,
2044 .stepping = 2,
2045 /* Missing: CPUID_DTS, CPUID_HT, CPUID_TM, CPUID_PBE */
2046 .features[FEAT_1_EDX] =
2047 PPRO_FEATURES |
2048 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_VME |
2049 CPUID_ACPI | CPUID_SS,
2050 /* Some CPUs got no CPUID_SEP */
2051 /* Missing: CPUID_EXT_DSCPL, CPUID_EXT_EST, CPUID_EXT_TM2,
2052 * CPUID_EXT_XTPR */
2053 .features[FEAT_1_ECX] =
2054 CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_SSSE3 |
2055 CPUID_EXT_MOVBE,
2056 .features[FEAT_8000_0001_EDX] =
2057 CPUID_EXT2_NX,
2058 .features[FEAT_8000_0001_ECX] =
2059 CPUID_EXT3_LAHF_LM,
2060 .xlevel = 0x80000008,
2061 .model_id = "Intel(R) Atom(TM) CPU N270 @ 1.60GHz",
2064 .name = "Conroe",
2065 .level = 10,
2066 .vendor = CPUID_VENDOR_INTEL,
2067 .family = 6,
2068 .model = 15,
2069 .stepping = 3,
2070 .features[FEAT_1_EDX] =
2071 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2072 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2073 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2074 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2075 CPUID_DE | CPUID_FP87,
2076 .features[FEAT_1_ECX] =
2077 CPUID_EXT_SSSE3 | CPUID_EXT_SSE3,
2078 .features[FEAT_8000_0001_EDX] =
2079 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
2080 .features[FEAT_8000_0001_ECX] =
2081 CPUID_EXT3_LAHF_LM,
2082 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS,
2083 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
2084 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
2085 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
2086 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2087 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS,
2088 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2089 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2090 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2091 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2092 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2093 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2094 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2095 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2096 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2097 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2098 .features[FEAT_VMX_SECONDARY_CTLS] =
2099 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES,
2100 .xlevel = 0x80000008,
2101 .model_id = "Intel Celeron_4x0 (Conroe/Merom Class Core 2)",
2104 .name = "Penryn",
2105 .level = 10,
2106 .vendor = CPUID_VENDOR_INTEL,
2107 .family = 6,
2108 .model = 23,
2109 .stepping = 3,
2110 .features[FEAT_1_EDX] =
2111 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2112 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2113 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2114 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2115 CPUID_DE | CPUID_FP87,
2116 .features[FEAT_1_ECX] =
2117 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2118 CPUID_EXT_SSE3,
2119 .features[FEAT_8000_0001_EDX] =
2120 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
2121 .features[FEAT_8000_0001_ECX] =
2122 CPUID_EXT3_LAHF_LM,
2123 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS,
2124 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2125 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL,
2126 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT |
2127 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL,
2128 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
2129 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2130 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS,
2131 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2132 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2133 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2134 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2135 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2136 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2137 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2138 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2139 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2140 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2141 .features[FEAT_VMX_SECONDARY_CTLS] =
2142 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2143 VMX_SECONDARY_EXEC_WBINVD_EXITING,
2144 .xlevel = 0x80000008,
2145 .model_id = "Intel Core 2 Duo P9xxx (Penryn Class Core 2)",
2148 .name = "Nehalem",
2149 .level = 11,
2150 .vendor = CPUID_VENDOR_INTEL,
2151 .family = 6,
2152 .model = 26,
2153 .stepping = 3,
2154 .features[FEAT_1_EDX] =
2155 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2156 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2157 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2158 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2159 CPUID_DE | CPUID_FP87,
2160 .features[FEAT_1_ECX] =
2161 CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
2162 CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_SSE3,
2163 .features[FEAT_8000_0001_EDX] =
2164 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
2165 .features[FEAT_8000_0001_ECX] =
2166 CPUID_EXT3_LAHF_LM,
2167 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2168 MSR_VMX_BASIC_TRUE_CTLS,
2169 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2170 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2171 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2172 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2173 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2174 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2175 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2176 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2177 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2178 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
2179 .features[FEAT_VMX_EXIT_CTLS] =
2180 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2181 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2182 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2183 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2184 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2185 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
2186 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2187 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2188 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
2189 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2190 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2191 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2192 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2193 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2194 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2195 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2196 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2197 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2198 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2199 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2200 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2201 .features[FEAT_VMX_SECONDARY_CTLS] =
2202 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2203 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2204 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2205 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2206 VMX_SECONDARY_EXEC_ENABLE_VPID,
2207 .xlevel = 0x80000008,
2208 .model_id = "Intel Core i7 9xx (Nehalem Class Core i7)",
2209 .versions = (X86CPUVersionDefinition[]) {
2210 { .version = 1 },
2212 .version = 2,
2213 .alias = "Nehalem-IBRS",
2214 .props = (PropValue[]) {
2215 { "spec-ctrl", "on" },
2216 { "model-id",
2217 "Intel Core i7 9xx (Nehalem Core i7, IBRS update)" },
2218 { /* end of list */ }
2221 { /* end of list */ }
2225 .name = "Westmere",
2226 .level = 11,
2227 .vendor = CPUID_VENDOR_INTEL,
2228 .family = 6,
2229 .model = 44,
2230 .stepping = 1,
2231 .features[FEAT_1_EDX] =
2232 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2233 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2234 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2235 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2236 CPUID_DE | CPUID_FP87,
2237 .features[FEAT_1_ECX] =
2238 CPUID_EXT_AES | CPUID_EXT_POPCNT | CPUID_EXT_SSE42 |
2239 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2240 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3,
2241 .features[FEAT_8000_0001_EDX] =
2242 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
2243 .features[FEAT_8000_0001_ECX] =
2244 CPUID_EXT3_LAHF_LM,
2245 .features[FEAT_6_EAX] =
2246 CPUID_6_EAX_ARAT,
2247 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2248 MSR_VMX_BASIC_TRUE_CTLS,
2249 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2250 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2251 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2252 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2253 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2254 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2255 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2256 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2257 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2258 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
2259 .features[FEAT_VMX_EXIT_CTLS] =
2260 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2261 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2262 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2263 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2264 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2265 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2266 MSR_VMX_MISC_STORE_LMA,
2267 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2268 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2269 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
2270 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2271 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2272 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2273 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2274 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2275 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2276 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2277 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2278 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2279 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2280 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2281 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2282 .features[FEAT_VMX_SECONDARY_CTLS] =
2283 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2284 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2285 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2286 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2287 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST,
2288 .xlevel = 0x80000008,
2289 .model_id = "Westmere E56xx/L56xx/X56xx (Nehalem-C)",
2290 .versions = (X86CPUVersionDefinition[]) {
2291 { .version = 1 },
2293 .version = 2,
2294 .alias = "Westmere-IBRS",
2295 .props = (PropValue[]) {
2296 { "spec-ctrl", "on" },
2297 { "model-id",
2298 "Westmere E56xx/L56xx/X56xx (IBRS update)" },
2299 { /* end of list */ }
2302 { /* end of list */ }
2306 .name = "SandyBridge",
2307 .level = 0xd,
2308 .vendor = CPUID_VENDOR_INTEL,
2309 .family = 6,
2310 .model = 42,
2311 .stepping = 1,
2312 .features[FEAT_1_EDX] =
2313 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2314 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2315 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2316 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2317 CPUID_DE | CPUID_FP87,
2318 .features[FEAT_1_ECX] =
2319 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2320 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_POPCNT |
2321 CPUID_EXT_X2APIC | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
2322 CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ |
2323 CPUID_EXT_SSE3,
2324 .features[FEAT_8000_0001_EDX] =
2325 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
2326 CPUID_EXT2_SYSCALL,
2327 .features[FEAT_8000_0001_ECX] =
2328 CPUID_EXT3_LAHF_LM,
2329 .features[FEAT_XSAVE] =
2330 CPUID_XSAVE_XSAVEOPT,
2331 .features[FEAT_6_EAX] =
2332 CPUID_6_EAX_ARAT,
2333 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2334 MSR_VMX_BASIC_TRUE_CTLS,
2335 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2336 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2337 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2338 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2339 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2340 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2341 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2342 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2343 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2344 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
2345 .features[FEAT_VMX_EXIT_CTLS] =
2346 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2347 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2348 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2349 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2350 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2351 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2352 MSR_VMX_MISC_STORE_LMA,
2353 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2354 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2355 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
2356 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2357 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2358 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2359 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2360 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2361 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2362 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2363 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2364 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2365 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2366 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2367 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2368 .features[FEAT_VMX_SECONDARY_CTLS] =
2369 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2370 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2371 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2372 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2373 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST,
2374 .xlevel = 0x80000008,
2375 .model_id = "Intel Xeon E312xx (Sandy Bridge)",
2376 .versions = (X86CPUVersionDefinition[]) {
2377 { .version = 1 },
2379 .version = 2,
2380 .alias = "SandyBridge-IBRS",
2381 .props = (PropValue[]) {
2382 { "spec-ctrl", "on" },
2383 { "model-id",
2384 "Intel Xeon E312xx (Sandy Bridge, IBRS update)" },
2385 { /* end of list */ }
2388 { /* end of list */ }
2392 .name = "IvyBridge",
2393 .level = 0xd,
2394 .vendor = CPUID_VENDOR_INTEL,
2395 .family = 6,
2396 .model = 58,
2397 .stepping = 9,
2398 .features[FEAT_1_EDX] =
2399 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2400 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2401 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2402 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2403 CPUID_DE | CPUID_FP87,
2404 .features[FEAT_1_ECX] =
2405 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2406 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_POPCNT |
2407 CPUID_EXT_X2APIC | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
2408 CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ |
2409 CPUID_EXT_SSE3 | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
2410 .features[FEAT_7_0_EBX] =
2411 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_SMEP |
2412 CPUID_7_0_EBX_ERMS,
2413 .features[FEAT_8000_0001_EDX] =
2414 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
2415 CPUID_EXT2_SYSCALL,
2416 .features[FEAT_8000_0001_ECX] =
2417 CPUID_EXT3_LAHF_LM,
2418 .features[FEAT_XSAVE] =
2419 CPUID_XSAVE_XSAVEOPT,
2420 .features[FEAT_6_EAX] =
2421 CPUID_6_EAX_ARAT,
2422 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2423 MSR_VMX_BASIC_TRUE_CTLS,
2424 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2425 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2426 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2427 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2428 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2429 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2430 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2431 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2432 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2433 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
2434 .features[FEAT_VMX_EXIT_CTLS] =
2435 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2436 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2437 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2438 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2439 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2440 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2441 MSR_VMX_MISC_STORE_LMA,
2442 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2443 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2444 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
2445 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2446 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2447 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2448 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2449 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2450 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2451 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2452 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2453 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2454 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2455 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2456 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2457 .features[FEAT_VMX_SECONDARY_CTLS] =
2458 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2459 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2460 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2461 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2462 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
2463 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
2464 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
2465 VMX_SECONDARY_EXEC_RDRAND_EXITING,
2466 .xlevel = 0x80000008,
2467 .model_id = "Intel Xeon E3-12xx v2 (Ivy Bridge)",
2468 .versions = (X86CPUVersionDefinition[]) {
2469 { .version = 1 },
2471 .version = 2,
2472 .alias = "IvyBridge-IBRS",
2473 .props = (PropValue[]) {
2474 { "spec-ctrl", "on" },
2475 { "model-id",
2476 "Intel Xeon E3-12xx v2 (Ivy Bridge, IBRS)" },
2477 { /* end of list */ }
2480 { /* end of list */ }
2484 .name = "Haswell",
2485 .level = 0xd,
2486 .vendor = CPUID_VENDOR_INTEL,
2487 .family = 6,
2488 .model = 60,
2489 .stepping = 4,
2490 .features[FEAT_1_EDX] =
2491 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2492 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2493 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2494 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2495 CPUID_DE | CPUID_FP87,
2496 .features[FEAT_1_ECX] =
2497 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2498 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
2499 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2500 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
2501 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
2502 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
2503 .features[FEAT_8000_0001_EDX] =
2504 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
2505 CPUID_EXT2_SYSCALL,
2506 .features[FEAT_8000_0001_ECX] =
2507 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM,
2508 .features[FEAT_7_0_EBX] =
2509 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
2510 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
2511 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
2512 CPUID_7_0_EBX_RTM,
2513 .features[FEAT_XSAVE] =
2514 CPUID_XSAVE_XSAVEOPT,
2515 .features[FEAT_6_EAX] =
2516 CPUID_6_EAX_ARAT,
2517 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2518 MSR_VMX_BASIC_TRUE_CTLS,
2519 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2520 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2521 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2522 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2523 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2524 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2525 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2526 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2527 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2528 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
2529 .features[FEAT_VMX_EXIT_CTLS] =
2530 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2531 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2532 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2533 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2534 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2535 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2536 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
2537 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2538 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2539 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
2540 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2541 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2542 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2543 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2544 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2545 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2546 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2547 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2548 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2549 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2550 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2551 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2552 .features[FEAT_VMX_SECONDARY_CTLS] =
2553 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2554 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2555 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2556 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2557 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
2558 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
2559 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
2560 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
2561 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS,
2562 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
2563 .xlevel = 0x80000008,
2564 .model_id = "Intel Core Processor (Haswell)",
2565 .versions = (X86CPUVersionDefinition[]) {
2566 { .version = 1 },
2568 .version = 2,
2569 .alias = "Haswell-noTSX",
2570 .props = (PropValue[]) {
2571 { "hle", "off" },
2572 { "rtm", "off" },
2573 { "stepping", "1" },
2574 { "model-id", "Intel Core Processor (Haswell, no TSX)", },
2575 { /* end of list */ }
2579 .version = 3,
2580 .alias = "Haswell-IBRS",
2581 .props = (PropValue[]) {
2582 /* Restore TSX features removed by -v2 above */
2583 { "hle", "on" },
2584 { "rtm", "on" },
2586 * Haswell and Haswell-IBRS had stepping=4 in
2587 * QEMU 4.0 and older
2589 { "stepping", "4" },
2590 { "spec-ctrl", "on" },
2591 { "model-id",
2592 "Intel Core Processor (Haswell, IBRS)" },
2593 { /* end of list */ }
2597 .version = 4,
2598 .alias = "Haswell-noTSX-IBRS",
2599 .props = (PropValue[]) {
2600 { "hle", "off" },
2601 { "rtm", "off" },
2602 /* spec-ctrl was already enabled by -v3 above */
2603 { "stepping", "1" },
2604 { "model-id",
2605 "Intel Core Processor (Haswell, no TSX, IBRS)" },
2606 { /* end of list */ }
2609 { /* end of list */ }
2613 .name = "Broadwell",
2614 .level = 0xd,
2615 .vendor = CPUID_VENDOR_INTEL,
2616 .family = 6,
2617 .model = 61,
2618 .stepping = 2,
2619 .features[FEAT_1_EDX] =
2620 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2621 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2622 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2623 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2624 CPUID_DE | CPUID_FP87,
2625 .features[FEAT_1_ECX] =
2626 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2627 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
2628 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2629 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
2630 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
2631 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
2632 .features[FEAT_8000_0001_EDX] =
2633 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
2634 CPUID_EXT2_SYSCALL,
2635 .features[FEAT_8000_0001_ECX] =
2636 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
2637 .features[FEAT_7_0_EBX] =
2638 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
2639 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
2640 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
2641 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
2642 CPUID_7_0_EBX_SMAP,
2643 .features[FEAT_XSAVE] =
2644 CPUID_XSAVE_XSAVEOPT,
2645 .features[FEAT_6_EAX] =
2646 CPUID_6_EAX_ARAT,
2647 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2648 MSR_VMX_BASIC_TRUE_CTLS,
2649 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2650 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2651 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2652 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2653 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2654 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2655 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2656 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2657 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2658 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
2659 .features[FEAT_VMX_EXIT_CTLS] =
2660 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2661 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2662 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2663 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2664 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2665 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2666 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
2667 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2668 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2669 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
2670 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2671 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2672 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2673 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2674 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2675 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2676 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2677 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2678 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2679 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2680 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2681 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2682 .features[FEAT_VMX_SECONDARY_CTLS] =
2683 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2684 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2685 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2686 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2687 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
2688 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
2689 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
2690 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
2691 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
2692 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
2693 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
2694 .xlevel = 0x80000008,
2695 .model_id = "Intel Core Processor (Broadwell)",
2696 .versions = (X86CPUVersionDefinition[]) {
2697 { .version = 1 },
2699 .version = 2,
2700 .alias = "Broadwell-noTSX",
2701 .props = (PropValue[]) {
2702 { "hle", "off" },
2703 { "rtm", "off" },
2704 { "model-id", "Intel Core Processor (Broadwell, no TSX)", },
2705 { /* end of list */ }
2709 .version = 3,
2710 .alias = "Broadwell-IBRS",
2711 .props = (PropValue[]) {
2712 /* Restore TSX features removed by -v2 above */
2713 { "hle", "on" },
2714 { "rtm", "on" },
2715 { "spec-ctrl", "on" },
2716 { "model-id",
2717 "Intel Core Processor (Broadwell, IBRS)" },
2718 { /* end of list */ }
2722 .version = 4,
2723 .alias = "Broadwell-noTSX-IBRS",
2724 .props = (PropValue[]) {
2725 { "hle", "off" },
2726 { "rtm", "off" },
2727 /* spec-ctrl was already enabled by -v3 above */
2728 { "model-id",
2729 "Intel Core Processor (Broadwell, no TSX, IBRS)" },
2730 { /* end of list */ }
2733 { /* end of list */ }
2737 .name = "Skylake-Client",
2738 .level = 0xd,
2739 .vendor = CPUID_VENDOR_INTEL,
2740 .family = 6,
2741 .model = 94,
2742 .stepping = 3,
2743 .features[FEAT_1_EDX] =
2744 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2745 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2746 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2747 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2748 CPUID_DE | CPUID_FP87,
2749 .features[FEAT_1_ECX] =
2750 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2751 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
2752 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2753 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
2754 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
2755 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
2756 .features[FEAT_8000_0001_EDX] =
2757 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
2758 CPUID_EXT2_SYSCALL,
2759 .features[FEAT_8000_0001_ECX] =
2760 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
2761 .features[FEAT_7_0_EBX] =
2762 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
2763 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
2764 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
2765 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
2766 CPUID_7_0_EBX_SMAP,
2767 /* XSAVES is added in version 4 */
2768 .features[FEAT_XSAVE] =
2769 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
2770 CPUID_XSAVE_XGETBV1,
2771 .features[FEAT_6_EAX] =
2772 CPUID_6_EAX_ARAT,
2773 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
2774 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2775 MSR_VMX_BASIC_TRUE_CTLS,
2776 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2777 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2778 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2779 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2780 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2781 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2782 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2783 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2784 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2785 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
2786 .features[FEAT_VMX_EXIT_CTLS] =
2787 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2788 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2789 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2790 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2791 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2792 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2793 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
2794 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2795 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2796 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
2797 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2798 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2799 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2800 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2801 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2802 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2803 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2804 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2805 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2806 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2807 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2808 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2809 .features[FEAT_VMX_SECONDARY_CTLS] =
2810 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2811 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2812 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2813 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
2814 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
2815 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
2816 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
2817 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
2818 .xlevel = 0x80000008,
2819 .model_id = "Intel Core Processor (Skylake)",
2820 .versions = (X86CPUVersionDefinition[]) {
2821 { .version = 1 },
2823 .version = 2,
2824 .alias = "Skylake-Client-IBRS",
2825 .props = (PropValue[]) {
2826 { "spec-ctrl", "on" },
2827 { "model-id",
2828 "Intel Core Processor (Skylake, IBRS)" },
2829 { /* end of list */ }
2833 .version = 3,
2834 .alias = "Skylake-Client-noTSX-IBRS",
2835 .props = (PropValue[]) {
2836 { "hle", "off" },
2837 { "rtm", "off" },
2838 { "model-id",
2839 "Intel Core Processor (Skylake, IBRS, no TSX)" },
2840 { /* end of list */ }
2844 .version = 4,
2845 .note = "IBRS, XSAVES, no TSX",
2846 .props = (PropValue[]) {
2847 { "xsaves", "on" },
2848 { "vmx-xsaves", "on" },
2849 { /* end of list */ }
2852 { /* end of list */ }
2856 .name = "Skylake-Server",
2857 .level = 0xd,
2858 .vendor = CPUID_VENDOR_INTEL,
2859 .family = 6,
2860 .model = 85,
2861 .stepping = 4,
2862 .features[FEAT_1_EDX] =
2863 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2864 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2865 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2866 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2867 CPUID_DE | CPUID_FP87,
2868 .features[FEAT_1_ECX] =
2869 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2870 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
2871 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2872 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
2873 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
2874 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
2875 .features[FEAT_8000_0001_EDX] =
2876 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
2877 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
2878 .features[FEAT_8000_0001_ECX] =
2879 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
2880 .features[FEAT_7_0_EBX] =
2881 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
2882 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
2883 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
2884 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
2885 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLWB |
2886 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
2887 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512CD |
2888 CPUID_7_0_EBX_AVX512VL | CPUID_7_0_EBX_CLFLUSHOPT,
2889 .features[FEAT_7_0_ECX] =
2890 CPUID_7_0_ECX_PKU,
2891 /* XSAVES is added in version 5 */
2892 .features[FEAT_XSAVE] =
2893 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
2894 CPUID_XSAVE_XGETBV1,
2895 .features[FEAT_6_EAX] =
2896 CPUID_6_EAX_ARAT,
2897 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
2898 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2899 MSR_VMX_BASIC_TRUE_CTLS,
2900 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2901 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2902 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2903 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2904 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2905 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2906 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2907 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2908 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2909 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
2910 .features[FEAT_VMX_EXIT_CTLS] =
2911 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2912 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2913 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2914 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2915 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2916 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2917 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
2918 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2919 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2920 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
2921 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2922 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2923 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2924 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2925 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2926 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2927 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2928 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2929 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2930 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2931 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2932 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2933 .features[FEAT_VMX_SECONDARY_CTLS] =
2934 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2935 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2936 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2937 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2938 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
2939 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
2940 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
2941 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
2942 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
2943 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
2944 .xlevel = 0x80000008,
2945 .model_id = "Intel Xeon Processor (Skylake)",
2946 .versions = (X86CPUVersionDefinition[]) {
2947 { .version = 1 },
2949 .version = 2,
2950 .alias = "Skylake-Server-IBRS",
2951 .props = (PropValue[]) {
2952 /* clflushopt was not added to Skylake-Server-IBRS */
2953 /* TODO: add -v3 including clflushopt */
2954 { "clflushopt", "off" },
2955 { "spec-ctrl", "on" },
2956 { "model-id",
2957 "Intel Xeon Processor (Skylake, IBRS)" },
2958 { /* end of list */ }
2962 .version = 3,
2963 .alias = "Skylake-Server-noTSX-IBRS",
2964 .props = (PropValue[]) {
2965 { "hle", "off" },
2966 { "rtm", "off" },
2967 { "model-id",
2968 "Intel Xeon Processor (Skylake, IBRS, no TSX)" },
2969 { /* end of list */ }
2973 .version = 4,
2974 .props = (PropValue[]) {
2975 { "vmx-eptp-switching", "on" },
2976 { /* end of list */ }
2980 .version = 5,
2981 .note = "IBRS, XSAVES, EPT switching, no TSX",
2982 .props = (PropValue[]) {
2983 { "xsaves", "on" },
2984 { "vmx-xsaves", "on" },
2985 { /* end of list */ }
2988 { /* end of list */ }
2992 .name = "Cascadelake-Server",
2993 .level = 0xd,
2994 .vendor = CPUID_VENDOR_INTEL,
2995 .family = 6,
2996 .model = 85,
2997 .stepping = 6,
2998 .features[FEAT_1_EDX] =
2999 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3000 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3001 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3002 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3003 CPUID_DE | CPUID_FP87,
3004 .features[FEAT_1_ECX] =
3005 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3006 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3007 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3008 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3009 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3010 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3011 .features[FEAT_8000_0001_EDX] =
3012 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
3013 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3014 .features[FEAT_8000_0001_ECX] =
3015 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3016 .features[FEAT_7_0_EBX] =
3017 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
3018 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
3019 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
3020 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
3021 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLWB |
3022 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
3023 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512CD |
3024 CPUID_7_0_EBX_AVX512VL | CPUID_7_0_EBX_CLFLUSHOPT,
3025 .features[FEAT_7_0_ECX] =
3026 CPUID_7_0_ECX_PKU |
3027 CPUID_7_0_ECX_AVX512VNNI,
3028 .features[FEAT_7_0_EDX] =
3029 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_SPEC_CTRL_SSBD,
3030 /* XSAVES is added in version 5 */
3031 .features[FEAT_XSAVE] =
3032 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3033 CPUID_XSAVE_XGETBV1,
3034 .features[FEAT_6_EAX] =
3035 CPUID_6_EAX_ARAT,
3036 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
3037 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3038 MSR_VMX_BASIC_TRUE_CTLS,
3039 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3040 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3041 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3042 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3043 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3044 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3045 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3046 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3047 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3048 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3049 .features[FEAT_VMX_EXIT_CTLS] =
3050 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3051 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3052 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3053 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3054 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3055 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3056 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3057 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3058 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3059 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3060 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3061 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3062 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3063 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3064 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3065 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3066 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3067 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3068 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3069 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3070 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3071 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3072 .features[FEAT_VMX_SECONDARY_CTLS] =
3073 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3074 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3075 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3076 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3077 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3078 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3079 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3080 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3081 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3082 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3083 .xlevel = 0x80000008,
3084 .model_id = "Intel Xeon Processor (Cascadelake)",
3085 .versions = (X86CPUVersionDefinition[]) {
3086 { .version = 1 },
3087 { .version = 2,
3088 .note = "ARCH_CAPABILITIES",
3089 .props = (PropValue[]) {
3090 { "arch-capabilities", "on" },
3091 { "rdctl-no", "on" },
3092 { "ibrs-all", "on" },
3093 { "skip-l1dfl-vmentry", "on" },
3094 { "mds-no", "on" },
3095 { /* end of list */ }
3098 { .version = 3,
3099 .alias = "Cascadelake-Server-noTSX",
3100 .note = "ARCH_CAPABILITIES, no TSX",
3101 .props = (PropValue[]) {
3102 { "hle", "off" },
3103 { "rtm", "off" },
3104 { /* end of list */ }
3107 { .version = 4,
3108 .note = "ARCH_CAPABILITIES, no TSX",
3109 .props = (PropValue[]) {
3110 { "vmx-eptp-switching", "on" },
3111 { /* end of list */ }
3114 { .version = 5,
3115 .note = "ARCH_CAPABILITIES, EPT switching, XSAVES, no TSX",
3116 .props = (PropValue[]) {
3117 { "xsaves", "on" },
3118 { "vmx-xsaves", "on" },
3119 { /* end of list */ }
3122 { /* end of list */ }
3126 .name = "Cooperlake",
3127 .level = 0xd,
3128 .vendor = CPUID_VENDOR_INTEL,
3129 .family = 6,
3130 .model = 85,
3131 .stepping = 10,
3132 .features[FEAT_1_EDX] =
3133 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3134 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3135 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3136 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3137 CPUID_DE | CPUID_FP87,
3138 .features[FEAT_1_ECX] =
3139 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3140 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3141 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3142 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3143 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3144 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3145 .features[FEAT_8000_0001_EDX] =
3146 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
3147 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3148 .features[FEAT_8000_0001_ECX] =
3149 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3150 .features[FEAT_7_0_EBX] =
3151 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
3152 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
3153 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
3154 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
3155 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLWB |
3156 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
3157 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512CD |
3158 CPUID_7_0_EBX_AVX512VL | CPUID_7_0_EBX_CLFLUSHOPT,
3159 .features[FEAT_7_0_ECX] =
3160 CPUID_7_0_ECX_PKU |
3161 CPUID_7_0_ECX_AVX512VNNI,
3162 .features[FEAT_7_0_EDX] =
3163 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_STIBP |
3164 CPUID_7_0_EDX_SPEC_CTRL_SSBD | CPUID_7_0_EDX_ARCH_CAPABILITIES,
3165 .features[FEAT_ARCH_CAPABILITIES] =
3166 MSR_ARCH_CAP_RDCL_NO | MSR_ARCH_CAP_IBRS_ALL |
3167 MSR_ARCH_CAP_SKIP_L1DFL_VMENTRY | MSR_ARCH_CAP_MDS_NO |
3168 MSR_ARCH_CAP_PSCHANGE_MC_NO | MSR_ARCH_CAP_TAA_NO,
3169 .features[FEAT_7_1_EAX] =
3170 CPUID_7_1_EAX_AVX512_BF16,
3171 /* XSAVES is added in version 2 */
3172 .features[FEAT_XSAVE] =
3173 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3174 CPUID_XSAVE_XGETBV1,
3175 .features[FEAT_6_EAX] =
3176 CPUID_6_EAX_ARAT,
3177 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
3178 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3179 MSR_VMX_BASIC_TRUE_CTLS,
3180 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3181 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3182 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3183 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3184 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3185 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3186 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3187 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3188 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3189 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3190 .features[FEAT_VMX_EXIT_CTLS] =
3191 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3192 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3193 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3194 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3195 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3196 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3197 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3198 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3199 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3200 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3201 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3202 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3203 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3204 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3205 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3206 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3207 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3208 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3209 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3210 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3211 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3212 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3213 .features[FEAT_VMX_SECONDARY_CTLS] =
3214 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3215 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3216 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3217 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3218 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3219 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3220 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3221 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3222 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3223 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3224 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
3225 .xlevel = 0x80000008,
3226 .model_id = "Intel Xeon Processor (Cooperlake)",
3227 .versions = (X86CPUVersionDefinition[]) {
3228 { .version = 1 },
3229 { .version = 2,
3230 .note = "XSAVES",
3231 .props = (PropValue[]) {
3232 { "xsaves", "on" },
3233 { "vmx-xsaves", "on" },
3234 { /* end of list */ }
3237 { /* end of list */ }
3241 .name = "Icelake-Client",
3242 .level = 0xd,
3243 .vendor = CPUID_VENDOR_INTEL,
3244 .family = 6,
3245 .model = 126,
3246 .stepping = 0,
3247 .features[FEAT_1_EDX] =
3248 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3249 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3250 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3251 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3252 CPUID_DE | CPUID_FP87,
3253 .features[FEAT_1_ECX] =
3254 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3255 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3256 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3257 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3258 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3259 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3260 .features[FEAT_8000_0001_EDX] =
3261 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
3262 CPUID_EXT2_SYSCALL,
3263 .features[FEAT_8000_0001_ECX] =
3264 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3265 .features[FEAT_8000_0008_EBX] =
3266 CPUID_8000_0008_EBX_WBNOINVD,
3267 .features[FEAT_7_0_EBX] =
3268 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
3269 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
3270 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
3271 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
3272 CPUID_7_0_EBX_SMAP,
3273 .features[FEAT_7_0_ECX] =
3274 CPUID_7_0_ECX_AVX512_VBMI | CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_PKU |
3275 CPUID_7_0_ECX_AVX512_VBMI2 | CPUID_7_0_ECX_GFNI |
3276 CPUID_7_0_ECX_VAES | CPUID_7_0_ECX_VPCLMULQDQ |
3277 CPUID_7_0_ECX_AVX512VNNI | CPUID_7_0_ECX_AVX512BITALG |
3278 CPUID_7_0_ECX_AVX512_VPOPCNTDQ,
3279 .features[FEAT_7_0_EDX] =
3280 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_SPEC_CTRL_SSBD,
3281 /* XSAVES is added in version 3 */
3282 .features[FEAT_XSAVE] =
3283 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3284 CPUID_XSAVE_XGETBV1,
3285 .features[FEAT_6_EAX] =
3286 CPUID_6_EAX_ARAT,
3287 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
3288 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3289 MSR_VMX_BASIC_TRUE_CTLS,
3290 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3291 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3292 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3293 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3294 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3295 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3296 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3297 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3298 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3299 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3300 .features[FEAT_VMX_EXIT_CTLS] =
3301 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3302 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3303 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3304 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3305 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3306 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3307 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3308 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3309 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3310 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
3311 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3312 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3313 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3314 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3315 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3316 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3317 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3318 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3319 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3320 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3321 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3322 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3323 .features[FEAT_VMX_SECONDARY_CTLS] =
3324 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3325 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3326 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3327 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3328 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3329 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3330 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3331 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
3332 .xlevel = 0x80000008,
3333 .model_id = "Intel Core Processor (Icelake)",
3334 .versions = (X86CPUVersionDefinition[]) {
3336 .version = 1,
3337 .note = "deprecated"
3340 .version = 2,
3341 .note = "no TSX, deprecated",
3342 .alias = "Icelake-Client-noTSX",
3343 .props = (PropValue[]) {
3344 { "hle", "off" },
3345 { "rtm", "off" },
3346 { /* end of list */ }
3350 .version = 3,
3351 .note = "no TSX, XSAVES, deprecated",
3352 .props = (PropValue[]) {
3353 { "xsaves", "on" },
3354 { "vmx-xsaves", "on" },
3355 { /* end of list */ }
3358 { /* end of list */ }
3360 .deprecation_note = "use Icelake-Server instead"
3363 .name = "Icelake-Server",
3364 .level = 0xd,
3365 .vendor = CPUID_VENDOR_INTEL,
3366 .family = 6,
3367 .model = 134,
3368 .stepping = 0,
3369 .features[FEAT_1_EDX] =
3370 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3371 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3372 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3373 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3374 CPUID_DE | CPUID_FP87,
3375 .features[FEAT_1_ECX] =
3376 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3377 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3378 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3379 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3380 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3381 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3382 .features[FEAT_8000_0001_EDX] =
3383 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
3384 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3385 .features[FEAT_8000_0001_ECX] =
3386 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3387 .features[FEAT_8000_0008_EBX] =
3388 CPUID_8000_0008_EBX_WBNOINVD,
3389 .features[FEAT_7_0_EBX] =
3390 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
3391 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
3392 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
3393 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
3394 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLWB |
3395 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
3396 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512CD |
3397 CPUID_7_0_EBX_AVX512VL | CPUID_7_0_EBX_CLFLUSHOPT,
3398 .features[FEAT_7_0_ECX] =
3399 CPUID_7_0_ECX_AVX512_VBMI | CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_PKU |
3400 CPUID_7_0_ECX_AVX512_VBMI2 | CPUID_7_0_ECX_GFNI |
3401 CPUID_7_0_ECX_VAES | CPUID_7_0_ECX_VPCLMULQDQ |
3402 CPUID_7_0_ECX_AVX512VNNI | CPUID_7_0_ECX_AVX512BITALG |
3403 CPUID_7_0_ECX_AVX512_VPOPCNTDQ | CPUID_7_0_ECX_LA57,
3404 .features[FEAT_7_0_EDX] =
3405 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_SPEC_CTRL_SSBD,
3406 /* XSAVES is added in version 5 */
3407 .features[FEAT_XSAVE] =
3408 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3409 CPUID_XSAVE_XGETBV1,
3410 .features[FEAT_6_EAX] =
3411 CPUID_6_EAX_ARAT,
3412 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
3413 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3414 MSR_VMX_BASIC_TRUE_CTLS,
3415 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3416 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3417 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3418 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3419 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3420 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3421 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3422 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3423 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3424 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3425 .features[FEAT_VMX_EXIT_CTLS] =
3426 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3427 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3428 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3429 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3430 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3431 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3432 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3433 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3434 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3435 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3436 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3437 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3438 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3439 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3440 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3441 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3442 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3443 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3444 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3445 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3446 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3447 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3448 .features[FEAT_VMX_SECONDARY_CTLS] =
3449 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3450 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3451 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3452 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3453 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3454 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3455 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3456 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3457 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS,
3458 .xlevel = 0x80000008,
3459 .model_id = "Intel Xeon Processor (Icelake)",
3460 .versions = (X86CPUVersionDefinition[]) {
3461 { .version = 1 },
3463 .version = 2,
3464 .note = "no TSX",
3465 .alias = "Icelake-Server-noTSX",
3466 .props = (PropValue[]) {
3467 { "hle", "off" },
3468 { "rtm", "off" },
3469 { /* end of list */ }
3473 .version = 3,
3474 .props = (PropValue[]) {
3475 { "arch-capabilities", "on" },
3476 { "rdctl-no", "on" },
3477 { "ibrs-all", "on" },
3478 { "skip-l1dfl-vmentry", "on" },
3479 { "mds-no", "on" },
3480 { "pschange-mc-no", "on" },
3481 { "taa-no", "on" },
3482 { /* end of list */ }
3486 .version = 4,
3487 .props = (PropValue[]) {
3488 { "sha-ni", "on" },
3489 { "avx512ifma", "on" },
3490 { "rdpid", "on" },
3491 { "fsrm", "on" },
3492 { "vmx-rdseed-exit", "on" },
3493 { "vmx-pml", "on" },
3494 { "vmx-eptp-switching", "on" },
3495 { "model", "106" },
3496 { /* end of list */ }
3500 .version = 5,
3501 .note = "XSAVES",
3502 .props = (PropValue[]) {
3503 { "xsaves", "on" },
3504 { "vmx-xsaves", "on" },
3505 { /* end of list */ }
3508 { /* end of list */ }
3512 .name = "Denverton",
3513 .level = 21,
3514 .vendor = CPUID_VENDOR_INTEL,
3515 .family = 6,
3516 .model = 95,
3517 .stepping = 1,
3518 .features[FEAT_1_EDX] =
3519 CPUID_FP87 | CPUID_VME | CPUID_DE | CPUID_PSE | CPUID_TSC |
3520 CPUID_MSR | CPUID_PAE | CPUID_MCE | CPUID_CX8 | CPUID_APIC |
3521 CPUID_SEP | CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV |
3522 CPUID_PAT | CPUID_PSE36 | CPUID_CLFLUSH | CPUID_MMX | CPUID_FXSR |
3523 CPUID_SSE | CPUID_SSE2,
3524 .features[FEAT_1_ECX] =
3525 CPUID_EXT_SSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_MONITOR |
3526 CPUID_EXT_SSSE3 | CPUID_EXT_CX16 | CPUID_EXT_SSE41 |
3527 CPUID_EXT_SSE42 | CPUID_EXT_X2APIC | CPUID_EXT_MOVBE |
3528 CPUID_EXT_POPCNT | CPUID_EXT_TSC_DEADLINE_TIMER |
3529 CPUID_EXT_AES | CPUID_EXT_XSAVE | CPUID_EXT_RDRAND,
3530 .features[FEAT_8000_0001_EDX] =
3531 CPUID_EXT2_SYSCALL | CPUID_EXT2_NX | CPUID_EXT2_PDPE1GB |
3532 CPUID_EXT2_RDTSCP | CPUID_EXT2_LM,
3533 .features[FEAT_8000_0001_ECX] =
3534 CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3535 .features[FEAT_7_0_EBX] =
3536 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_ERMS |
3537 CPUID_7_0_EBX_MPX | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_SMAP |
3538 CPUID_7_0_EBX_CLFLUSHOPT | CPUID_7_0_EBX_SHA_NI,
3539 .features[FEAT_7_0_EDX] =
3540 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_ARCH_CAPABILITIES |
3541 CPUID_7_0_EDX_SPEC_CTRL_SSBD,
3542 /* XSAVES is added in version 3 */
3543 .features[FEAT_XSAVE] =
3544 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC | CPUID_XSAVE_XGETBV1,
3545 .features[FEAT_6_EAX] =
3546 CPUID_6_EAX_ARAT,
3547 .features[FEAT_ARCH_CAPABILITIES] =
3548 MSR_ARCH_CAP_RDCL_NO | MSR_ARCH_CAP_SKIP_L1DFL_VMENTRY,
3549 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3550 MSR_VMX_BASIC_TRUE_CTLS,
3551 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3552 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3553 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3554 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3555 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3556 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3557 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3558 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3559 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3560 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3561 .features[FEAT_VMX_EXIT_CTLS] =
3562 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3563 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3564 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3565 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3566 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3567 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3568 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3569 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3570 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3571 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3572 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3573 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3574 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3575 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3576 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3577 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3578 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3579 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3580 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3581 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3582 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3583 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3584 .features[FEAT_VMX_SECONDARY_CTLS] =
3585 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3586 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3587 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3588 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3589 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3590 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3591 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3592 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3593 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3594 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3595 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
3596 .xlevel = 0x80000008,
3597 .model_id = "Intel Atom Processor (Denverton)",
3598 .versions = (X86CPUVersionDefinition[]) {
3599 { .version = 1 },
3601 .version = 2,
3602 .note = "no MPX, no MONITOR",
3603 .props = (PropValue[]) {
3604 { "monitor", "off" },
3605 { "mpx", "off" },
3606 { /* end of list */ },
3610 .version = 3,
3611 .note = "XSAVES, no MPX, no MONITOR",
3612 .props = (PropValue[]) {
3613 { "xsaves", "on" },
3614 { "vmx-xsaves", "on" },
3615 { /* end of list */ },
3618 { /* end of list */ },
3622 .name = "Snowridge",
3623 .level = 27,
3624 .vendor = CPUID_VENDOR_INTEL,
3625 .family = 6,
3626 .model = 134,
3627 .stepping = 1,
3628 .features[FEAT_1_EDX] =
3629 /* missing: CPUID_PN CPUID_IA64 */
3630 /* missing: CPUID_DTS, CPUID_HT, CPUID_TM, CPUID_PBE */
3631 CPUID_FP87 | CPUID_VME | CPUID_DE | CPUID_PSE |
3632 CPUID_TSC | CPUID_MSR | CPUID_PAE | CPUID_MCE |
3633 CPUID_CX8 | CPUID_APIC | CPUID_SEP |
3634 CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV |
3635 CPUID_PAT | CPUID_PSE36 | CPUID_CLFLUSH |
3636 CPUID_MMX |
3637 CPUID_FXSR | CPUID_SSE | CPUID_SSE2,
3638 .features[FEAT_1_ECX] =
3639 CPUID_EXT_SSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_MONITOR |
3640 CPUID_EXT_SSSE3 |
3641 CPUID_EXT_CX16 |
3642 CPUID_EXT_SSE41 |
3643 CPUID_EXT_SSE42 | CPUID_EXT_X2APIC | CPUID_EXT_MOVBE |
3644 CPUID_EXT_POPCNT |
3645 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_AES | CPUID_EXT_XSAVE |
3646 CPUID_EXT_RDRAND,
3647 .features[FEAT_8000_0001_EDX] =
3648 CPUID_EXT2_SYSCALL |
3649 CPUID_EXT2_NX |
3650 CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
3651 CPUID_EXT2_LM,
3652 .features[FEAT_8000_0001_ECX] =
3653 CPUID_EXT3_LAHF_LM |
3654 CPUID_EXT3_3DNOWPREFETCH,
3655 .features[FEAT_7_0_EBX] =
3656 CPUID_7_0_EBX_FSGSBASE |
3657 CPUID_7_0_EBX_SMEP |
3658 CPUID_7_0_EBX_ERMS |
3659 CPUID_7_0_EBX_MPX | /* missing bits 13, 15 */
3660 CPUID_7_0_EBX_RDSEED |
3661 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT |
3662 CPUID_7_0_EBX_CLWB |
3663 CPUID_7_0_EBX_SHA_NI,
3664 .features[FEAT_7_0_ECX] =
3665 CPUID_7_0_ECX_UMIP |
3666 /* missing bit 5 */
3667 CPUID_7_0_ECX_GFNI |
3668 CPUID_7_0_ECX_MOVDIRI | CPUID_7_0_ECX_CLDEMOTE |
3669 CPUID_7_0_ECX_MOVDIR64B,
3670 .features[FEAT_7_0_EDX] =
3671 CPUID_7_0_EDX_SPEC_CTRL |
3672 CPUID_7_0_EDX_ARCH_CAPABILITIES | CPUID_7_0_EDX_SPEC_CTRL_SSBD |
3673 CPUID_7_0_EDX_CORE_CAPABILITY,
3674 .features[FEAT_CORE_CAPABILITY] =
3675 MSR_CORE_CAP_SPLIT_LOCK_DETECT,
3676 /* XSAVES is is added in version 3 */
3677 .features[FEAT_XSAVE] =
3678 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3679 CPUID_XSAVE_XGETBV1,
3680 .features[FEAT_6_EAX] =
3681 CPUID_6_EAX_ARAT,
3682 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3683 MSR_VMX_BASIC_TRUE_CTLS,
3684 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3685 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3686 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3687 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3688 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3689 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3690 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3691 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3692 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3693 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3694 .features[FEAT_VMX_EXIT_CTLS] =
3695 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3696 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3697 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3698 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3699 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3700 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3701 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3702 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3703 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3704 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3705 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3706 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3707 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3708 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3709 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3710 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3711 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3712 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3713 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3714 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3715 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3716 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3717 .features[FEAT_VMX_SECONDARY_CTLS] =
3718 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3719 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3720 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3721 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3722 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3723 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3724 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3725 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3726 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3727 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3728 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
3729 .xlevel = 0x80000008,
3730 .model_id = "Intel Atom Processor (SnowRidge)",
3731 .versions = (X86CPUVersionDefinition[]) {
3732 { .version = 1 },
3734 .version = 2,
3735 .props = (PropValue[]) {
3736 { "mpx", "off" },
3737 { "model-id", "Intel Atom Processor (Snowridge, no MPX)" },
3738 { /* end of list */ },
3742 .version = 3,
3743 .note = "XSAVES, no MPX",
3744 .props = (PropValue[]) {
3745 { "xsaves", "on" },
3746 { "vmx-xsaves", "on" },
3747 { /* end of list */ },
3751 .version = 4,
3752 .note = "no split lock detect, no core-capability",
3753 .props = (PropValue[]) {
3754 { "split-lock-detect", "off" },
3755 { "core-capability", "off" },
3756 { /* end of list */ },
3759 { /* end of list */ },
3763 .name = "KnightsMill",
3764 .level = 0xd,
3765 .vendor = CPUID_VENDOR_INTEL,
3766 .family = 6,
3767 .model = 133,
3768 .stepping = 0,
3769 .features[FEAT_1_EDX] =
3770 CPUID_VME | CPUID_SS | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR |
3771 CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV |
3772 CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC |
3773 CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC |
3774 CPUID_PSE | CPUID_DE | CPUID_FP87,
3775 .features[FEAT_1_ECX] =
3776 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3777 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3778 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3779 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3780 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3781 CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3782 .features[FEAT_8000_0001_EDX] =
3783 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
3784 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3785 .features[FEAT_8000_0001_ECX] =
3786 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3787 .features[FEAT_7_0_EBX] =
3788 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
3789 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS |
3790 CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_AVX512F |
3791 CPUID_7_0_EBX_AVX512CD | CPUID_7_0_EBX_AVX512PF |
3792 CPUID_7_0_EBX_AVX512ER,
3793 .features[FEAT_7_0_ECX] =
3794 CPUID_7_0_ECX_AVX512_VPOPCNTDQ,
3795 .features[FEAT_7_0_EDX] =
3796 CPUID_7_0_EDX_AVX512_4VNNIW | CPUID_7_0_EDX_AVX512_4FMAPS,
3797 .features[FEAT_XSAVE] =
3798 CPUID_XSAVE_XSAVEOPT,
3799 .features[FEAT_6_EAX] =
3800 CPUID_6_EAX_ARAT,
3801 .xlevel = 0x80000008,
3802 .model_id = "Intel Xeon Phi Processor (Knights Mill)",
3805 .name = "Opteron_G1",
3806 .level = 5,
3807 .vendor = CPUID_VENDOR_AMD,
3808 .family = 15,
3809 .model = 6,
3810 .stepping = 1,
3811 .features[FEAT_1_EDX] =
3812 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3813 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3814 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3815 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3816 CPUID_DE | CPUID_FP87,
3817 .features[FEAT_1_ECX] =
3818 CPUID_EXT_SSE3,
3819 .features[FEAT_8000_0001_EDX] =
3820 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3821 .xlevel = 0x80000008,
3822 .model_id = "AMD Opteron 240 (Gen 1 Class Opteron)",
3825 .name = "Opteron_G2",
3826 .level = 5,
3827 .vendor = CPUID_VENDOR_AMD,
3828 .family = 15,
3829 .model = 6,
3830 .stepping = 1,
3831 .features[FEAT_1_EDX] =
3832 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3833 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3834 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3835 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3836 CPUID_DE | CPUID_FP87,
3837 .features[FEAT_1_ECX] =
3838 CPUID_EXT_CX16 | CPUID_EXT_SSE3,
3839 .features[FEAT_8000_0001_EDX] =
3840 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3841 .features[FEAT_8000_0001_ECX] =
3842 CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM,
3843 .xlevel = 0x80000008,
3844 .model_id = "AMD Opteron 22xx (Gen 2 Class Opteron)",
3847 .name = "Opteron_G3",
3848 .level = 5,
3849 .vendor = CPUID_VENDOR_AMD,
3850 .family = 16,
3851 .model = 2,
3852 .stepping = 3,
3853 .features[FEAT_1_EDX] =
3854 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3855 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3856 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3857 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3858 CPUID_DE | CPUID_FP87,
3859 .features[FEAT_1_ECX] =
3860 CPUID_EXT_POPCNT | CPUID_EXT_CX16 | CPUID_EXT_MONITOR |
3861 CPUID_EXT_SSE3,
3862 .features[FEAT_8000_0001_EDX] =
3863 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL |
3864 CPUID_EXT2_RDTSCP,
3865 .features[FEAT_8000_0001_ECX] =
3866 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A |
3867 CPUID_EXT3_ABM | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM,
3868 .xlevel = 0x80000008,
3869 .model_id = "AMD Opteron 23xx (Gen 3 Class Opteron)",
3872 .name = "Opteron_G4",
3873 .level = 0xd,
3874 .vendor = CPUID_VENDOR_AMD,
3875 .family = 21,
3876 .model = 1,
3877 .stepping = 2,
3878 .features[FEAT_1_EDX] =
3879 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3880 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3881 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3882 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3883 CPUID_DE | CPUID_FP87,
3884 .features[FEAT_1_ECX] =
3885 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3886 CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
3887 CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ |
3888 CPUID_EXT_SSE3,
3889 .features[FEAT_8000_0001_EDX] =
3890 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_NX |
3891 CPUID_EXT2_SYSCALL | CPUID_EXT2_RDTSCP,
3892 .features[FEAT_8000_0001_ECX] =
3893 CPUID_EXT3_FMA4 | CPUID_EXT3_XOP |
3894 CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_MISALIGNSSE |
3895 CPUID_EXT3_SSE4A | CPUID_EXT3_ABM | CPUID_EXT3_SVM |
3896 CPUID_EXT3_LAHF_LM,
3897 .features[FEAT_SVM] =
3898 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
3899 /* no xsaveopt! */
3900 .xlevel = 0x8000001A,
3901 .model_id = "AMD Opteron 62xx class CPU",
3904 .name = "Opteron_G5",
3905 .level = 0xd,
3906 .vendor = CPUID_VENDOR_AMD,
3907 .family = 21,
3908 .model = 2,
3909 .stepping = 0,
3910 .features[FEAT_1_EDX] =
3911 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3912 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3913 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3914 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3915 CPUID_DE | CPUID_FP87,
3916 .features[FEAT_1_ECX] =
3917 CPUID_EXT_F16C | CPUID_EXT_AVX | CPUID_EXT_XSAVE |
3918 CPUID_EXT_AES | CPUID_EXT_POPCNT | CPUID_EXT_SSE42 |
3919 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_FMA |
3920 CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3,
3921 .features[FEAT_8000_0001_EDX] =
3922 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_NX |
3923 CPUID_EXT2_SYSCALL | CPUID_EXT2_RDTSCP,
3924 .features[FEAT_8000_0001_ECX] =
3925 CPUID_EXT3_TBM | CPUID_EXT3_FMA4 | CPUID_EXT3_XOP |
3926 CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_MISALIGNSSE |
3927 CPUID_EXT3_SSE4A | CPUID_EXT3_ABM | CPUID_EXT3_SVM |
3928 CPUID_EXT3_LAHF_LM,
3929 .features[FEAT_SVM] =
3930 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
3931 /* no xsaveopt! */
3932 .xlevel = 0x8000001A,
3933 .model_id = "AMD Opteron 63xx class CPU",
3936 .name = "EPYC",
3937 .level = 0xd,
3938 .vendor = CPUID_VENDOR_AMD,
3939 .family = 23,
3940 .model = 1,
3941 .stepping = 2,
3942 .features[FEAT_1_EDX] =
3943 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
3944 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
3945 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
3946 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
3947 CPUID_VME | CPUID_FP87,
3948 .features[FEAT_1_ECX] =
3949 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
3950 CPUID_EXT_XSAVE | CPUID_EXT_AES | CPUID_EXT_POPCNT |
3951 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
3952 CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 |
3953 CPUID_EXT_MONITOR | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3,
3954 .features[FEAT_8000_0001_EDX] =
3955 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
3956 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
3957 CPUID_EXT2_SYSCALL,
3958 .features[FEAT_8000_0001_ECX] =
3959 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
3960 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
3961 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
3962 CPUID_EXT3_TOPOEXT,
3963 .features[FEAT_7_0_EBX] =
3964 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
3965 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_RDSEED |
3966 CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT |
3967 CPUID_7_0_EBX_SHA_NI,
3968 .features[FEAT_XSAVE] =
3969 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3970 CPUID_XSAVE_XGETBV1,
3971 .features[FEAT_6_EAX] =
3972 CPUID_6_EAX_ARAT,
3973 .features[FEAT_SVM] =
3974 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
3975 .xlevel = 0x8000001E,
3976 .model_id = "AMD EPYC Processor",
3977 .cache_info = &epyc_cache_info,
3978 .versions = (X86CPUVersionDefinition[]) {
3979 { .version = 1 },
3981 .version = 2,
3982 .alias = "EPYC-IBPB",
3983 .props = (PropValue[]) {
3984 { "ibpb", "on" },
3985 { "model-id",
3986 "AMD EPYC Processor (with IBPB)" },
3987 { /* end of list */ }
3991 .version = 3,
3992 .props = (PropValue[]) {
3993 { "ibpb", "on" },
3994 { "perfctr-core", "on" },
3995 { "clzero", "on" },
3996 { "xsaveerptr", "on" },
3997 { "xsaves", "on" },
3998 { "model-id",
3999 "AMD EPYC Processor" },
4000 { /* end of list */ }
4003 { /* end of list */ }
4007 .name = "Dhyana",
4008 .level = 0xd,
4009 .vendor = CPUID_VENDOR_HYGON,
4010 .family = 24,
4011 .model = 0,
4012 .stepping = 1,
4013 .features[FEAT_1_EDX] =
4014 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
4015 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
4016 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
4017 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
4018 CPUID_VME | CPUID_FP87,
4019 .features[FEAT_1_ECX] =
4020 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
4021 CPUID_EXT_XSAVE | CPUID_EXT_POPCNT |
4022 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
4023 CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 |
4024 CPUID_EXT_MONITOR | CPUID_EXT_SSE3,
4025 .features[FEAT_8000_0001_EDX] =
4026 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
4027 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
4028 CPUID_EXT2_SYSCALL,
4029 .features[FEAT_8000_0001_ECX] =
4030 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
4031 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
4032 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
4033 CPUID_EXT3_TOPOEXT,
4034 .features[FEAT_8000_0008_EBX] =
4035 CPUID_8000_0008_EBX_IBPB,
4036 .features[FEAT_7_0_EBX] =
4037 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
4038 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_RDSEED |
4039 CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT,
4040 /* XSAVES is added in version 2 */
4041 .features[FEAT_XSAVE] =
4042 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
4043 CPUID_XSAVE_XGETBV1,
4044 .features[FEAT_6_EAX] =
4045 CPUID_6_EAX_ARAT,
4046 .features[FEAT_SVM] =
4047 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
4048 .xlevel = 0x8000001E,
4049 .model_id = "Hygon Dhyana Processor",
4050 .cache_info = &epyc_cache_info,
4051 .versions = (X86CPUVersionDefinition[]) {
4052 { .version = 1 },
4053 { .version = 2,
4054 .note = "XSAVES",
4055 .props = (PropValue[]) {
4056 { "xsaves", "on" },
4057 { /* end of list */ }
4060 { /* end of list */ }
4064 .name = "EPYC-Rome",
4065 .level = 0xd,
4066 .vendor = CPUID_VENDOR_AMD,
4067 .family = 23,
4068 .model = 49,
4069 .stepping = 0,
4070 .features[FEAT_1_EDX] =
4071 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
4072 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
4073 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
4074 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
4075 CPUID_VME | CPUID_FP87,
4076 .features[FEAT_1_ECX] =
4077 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
4078 CPUID_EXT_XSAVE | CPUID_EXT_AES | CPUID_EXT_POPCNT |
4079 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
4080 CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 |
4081 CPUID_EXT_MONITOR | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3,
4082 .features[FEAT_8000_0001_EDX] =
4083 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
4084 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
4085 CPUID_EXT2_SYSCALL,
4086 .features[FEAT_8000_0001_ECX] =
4087 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
4088 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
4089 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
4090 CPUID_EXT3_TOPOEXT | CPUID_EXT3_PERFCORE,
4091 .features[FEAT_8000_0008_EBX] =
4092 CPUID_8000_0008_EBX_CLZERO | CPUID_8000_0008_EBX_XSAVEERPTR |
4093 CPUID_8000_0008_EBX_WBNOINVD | CPUID_8000_0008_EBX_IBPB |
4094 CPUID_8000_0008_EBX_STIBP,
4095 .features[FEAT_7_0_EBX] =
4096 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
4097 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_RDSEED |
4098 CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT |
4099 CPUID_7_0_EBX_SHA_NI | CPUID_7_0_EBX_CLWB,
4100 .features[FEAT_7_0_ECX] =
4101 CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_RDPID,
4102 .features[FEAT_XSAVE] =
4103 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
4104 CPUID_XSAVE_XGETBV1 | CPUID_XSAVE_XSAVES,
4105 .features[FEAT_6_EAX] =
4106 CPUID_6_EAX_ARAT,
4107 .features[FEAT_SVM] =
4108 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
4109 .xlevel = 0x8000001E,
4110 .model_id = "AMD EPYC-Rome Processor",
4111 .cache_info = &epyc_rome_cache_info,
4112 .versions = (X86CPUVersionDefinition[]) {
4113 { .version = 1 },
4115 .version = 2,
4116 .props = (PropValue[]) {
4117 { "ibrs", "on" },
4118 { "amd-ssbd", "on" },
4119 { /* end of list */ }
4122 { /* end of list */ }
4126 .name = "EPYC-Milan",
4127 .level = 0xd,
4128 .vendor = CPUID_VENDOR_AMD,
4129 .family = 25,
4130 .model = 1,
4131 .stepping = 1,
4132 .features[FEAT_1_EDX] =
4133 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
4134 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
4135 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
4136 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
4137 CPUID_VME | CPUID_FP87,
4138 .features[FEAT_1_ECX] =
4139 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
4140 CPUID_EXT_XSAVE | CPUID_EXT_AES | CPUID_EXT_POPCNT |
4141 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
4142 CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 |
4143 CPUID_EXT_MONITOR | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
4144 CPUID_EXT_PCID,
4145 .features[FEAT_8000_0001_EDX] =
4146 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
4147 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
4148 CPUID_EXT2_SYSCALL,
4149 .features[FEAT_8000_0001_ECX] =
4150 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
4151 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
4152 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
4153 CPUID_EXT3_TOPOEXT | CPUID_EXT3_PERFCORE,
4154 .features[FEAT_8000_0008_EBX] =
4155 CPUID_8000_0008_EBX_CLZERO | CPUID_8000_0008_EBX_XSAVEERPTR |
4156 CPUID_8000_0008_EBX_WBNOINVD | CPUID_8000_0008_EBX_IBPB |
4157 CPUID_8000_0008_EBX_IBRS | CPUID_8000_0008_EBX_STIBP |
4158 CPUID_8000_0008_EBX_AMD_SSBD,
4159 .features[FEAT_7_0_EBX] =
4160 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
4161 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_RDSEED |
4162 CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT |
4163 CPUID_7_0_EBX_SHA_NI | CPUID_7_0_EBX_CLWB | CPUID_7_0_EBX_ERMS |
4164 CPUID_7_0_EBX_INVPCID,
4165 .features[FEAT_7_0_ECX] =
4166 CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_RDPID | CPUID_7_0_ECX_PKU,
4167 .features[FEAT_7_0_EDX] =
4168 CPUID_7_0_EDX_FSRM,
4169 .features[FEAT_XSAVE] =
4170 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
4171 CPUID_XSAVE_XGETBV1 | CPUID_XSAVE_XSAVES,
4172 .features[FEAT_6_EAX] =
4173 CPUID_6_EAX_ARAT,
4174 .features[FEAT_SVM] =
4175 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE | CPUID_SVM_SVME_ADDR_CHK,
4176 .xlevel = 0x8000001E,
4177 .model_id = "AMD EPYC-Milan Processor",
4178 .cache_info = &epyc_milan_cache_info,
4183 * We resolve CPU model aliases using -v1 when using "-machine
4184 * none", but this is just for compatibility while libvirt isn't
4185 * adapted to resolve CPU model versions before creating VMs.
4186 * See "Runnability guarantee of CPU models" at
4187 * docs/about/deprecated.rst.
4189 X86CPUVersion default_cpu_version = 1;
4191 void x86_cpu_set_default_version(X86CPUVersion version)
4193 /* Translating CPU_VERSION_AUTO to CPU_VERSION_AUTO doesn't make sense */
4194 assert(version != CPU_VERSION_AUTO);
4195 default_cpu_version = version;
4198 static X86CPUVersion x86_cpu_model_last_version(const X86CPUModel *model)
4200 int v = 0;
4201 const X86CPUVersionDefinition *vdef =
4202 x86_cpu_def_get_versions(model->cpudef);
4203 while (vdef->version) {
4204 v = vdef->version;
4205 vdef++;
4207 return v;
4210 /* Return the actual version being used for a specific CPU model */
4211 static X86CPUVersion x86_cpu_model_resolve_version(const X86CPUModel *model)
4213 X86CPUVersion v = model->version;
4214 if (v == CPU_VERSION_AUTO) {
4215 v = default_cpu_version;
4217 if (v == CPU_VERSION_LATEST) {
4218 return x86_cpu_model_last_version(model);
4220 return v;
4223 static Property max_x86_cpu_properties[] = {
4224 DEFINE_PROP_BOOL("migratable", X86CPU, migratable, true),
4225 DEFINE_PROP_BOOL("host-cache-info", X86CPU, cache_info_passthrough, false),
4226 DEFINE_PROP_END_OF_LIST()
4229 static void max_x86_cpu_class_init(ObjectClass *oc, void *data)
4231 DeviceClass *dc = DEVICE_CLASS(oc);
4232 X86CPUClass *xcc = X86_CPU_CLASS(oc);
4234 xcc->ordering = 9;
4236 xcc->model_description =
4237 "Enables all features supported by the accelerator in the current host";
4239 device_class_set_props(dc, max_x86_cpu_properties);
4242 static void max_x86_cpu_initfn(Object *obj)
4244 X86CPU *cpu = X86_CPU(obj);
4246 /* We can't fill the features array here because we don't know yet if
4247 * "migratable" is true or false.
4249 cpu->max_features = true;
4250 object_property_set_bool(OBJECT(cpu), "pmu", true, &error_abort);
4253 * these defaults are used for TCG and all other accelerators
4254 * besides KVM and HVF, which overwrite these values
4256 object_property_set_str(OBJECT(cpu), "vendor", CPUID_VENDOR_AMD,
4257 &error_abort);
4258 #ifdef TARGET_X86_64
4259 object_property_set_int(OBJECT(cpu), "family", 15, &error_abort);
4260 object_property_set_int(OBJECT(cpu), "model", 107, &error_abort);
4261 object_property_set_int(OBJECT(cpu), "stepping", 1, &error_abort);
4262 #else
4263 object_property_set_int(OBJECT(cpu), "family", 6, &error_abort);
4264 object_property_set_int(OBJECT(cpu), "model", 6, &error_abort);
4265 object_property_set_int(OBJECT(cpu), "stepping", 3, &error_abort);
4266 #endif
4267 object_property_set_str(OBJECT(cpu), "model-id",
4268 "QEMU TCG CPU version " QEMU_HW_VERSION,
4269 &error_abort);
4272 static const TypeInfo max_x86_cpu_type_info = {
4273 .name = X86_CPU_TYPE_NAME("max"),
4274 .parent = TYPE_X86_CPU,
4275 .instance_init = max_x86_cpu_initfn,
4276 .class_init = max_x86_cpu_class_init,
4279 static char *feature_word_description(FeatureWordInfo *f, uint32_t bit)
4281 assert(f->type == CPUID_FEATURE_WORD || f->type == MSR_FEATURE_WORD);
4283 switch (f->type) {
4284 case CPUID_FEATURE_WORD:
4286 const char *reg = get_register_name_32(f->cpuid.reg);
4287 assert(reg);
4288 return g_strdup_printf("CPUID.%02XH:%s",
4289 f->cpuid.eax, reg);
4291 case MSR_FEATURE_WORD:
4292 return g_strdup_printf("MSR(%02XH)",
4293 f->msr.index);
4296 return NULL;
4299 static bool x86_cpu_have_filtered_features(X86CPU *cpu)
4301 FeatureWord w;
4303 for (w = 0; w < FEATURE_WORDS; w++) {
4304 if (cpu->filtered_features[w]) {
4305 return true;
4309 return false;
4312 static void mark_unavailable_features(X86CPU *cpu, FeatureWord w, uint64_t mask,
4313 const char *verbose_prefix)
4315 CPUX86State *env = &cpu->env;
4316 FeatureWordInfo *f = &feature_word_info[w];
4317 int i;
4319 if (!cpu->force_features) {
4320 env->features[w] &= ~mask;
4322 cpu->filtered_features[w] |= mask;
4324 if (!verbose_prefix) {
4325 return;
4328 for (i = 0; i < 64; ++i) {
4329 if ((1ULL << i) & mask) {
4330 g_autofree char *feat_word_str = feature_word_description(f, i);
4331 warn_report("%s: %s%s%s [bit %d]",
4332 verbose_prefix,
4333 feat_word_str,
4334 f->feat_names[i] ? "." : "",
4335 f->feat_names[i] ? f->feat_names[i] : "", i);
4340 static void x86_cpuid_version_get_family(Object *obj, Visitor *v,
4341 const char *name, void *opaque,
4342 Error **errp)
4344 X86CPU *cpu = X86_CPU(obj);
4345 CPUX86State *env = &cpu->env;
4346 int64_t value;
4348 value = (env->cpuid_version >> 8) & 0xf;
4349 if (value == 0xf) {
4350 value += (env->cpuid_version >> 20) & 0xff;
4352 visit_type_int(v, name, &value, errp);
4355 static void x86_cpuid_version_set_family(Object *obj, Visitor *v,
4356 const char *name, void *opaque,
4357 Error **errp)
4359 X86CPU *cpu = X86_CPU(obj);
4360 CPUX86State *env = &cpu->env;
4361 const int64_t min = 0;
4362 const int64_t max = 0xff + 0xf;
4363 int64_t value;
4365 if (!visit_type_int(v, name, &value, errp)) {
4366 return;
4368 if (value < min || value > max) {
4369 error_setg(errp, QERR_PROPERTY_VALUE_OUT_OF_RANGE, "",
4370 name ? name : "null", value, min, max);
4371 return;
4374 env->cpuid_version &= ~0xff00f00;
4375 if (value > 0x0f) {
4376 env->cpuid_version |= 0xf00 | ((value - 0x0f) << 20);
4377 } else {
4378 env->cpuid_version |= value << 8;
4382 static void x86_cpuid_version_get_model(Object *obj, Visitor *v,
4383 const char *name, void *opaque,
4384 Error **errp)
4386 X86CPU *cpu = X86_CPU(obj);
4387 CPUX86State *env = &cpu->env;
4388 int64_t value;
4390 value = (env->cpuid_version >> 4) & 0xf;
4391 value |= ((env->cpuid_version >> 16) & 0xf) << 4;
4392 visit_type_int(v, name, &value, errp);
4395 static void x86_cpuid_version_set_model(Object *obj, Visitor *v,
4396 const char *name, void *opaque,
4397 Error **errp)
4399 X86CPU *cpu = X86_CPU(obj);
4400 CPUX86State *env = &cpu->env;
4401 const int64_t min = 0;
4402 const int64_t max = 0xff;
4403 int64_t value;
4405 if (!visit_type_int(v, name, &value, errp)) {
4406 return;
4408 if (value < min || value > max) {
4409 error_setg(errp, QERR_PROPERTY_VALUE_OUT_OF_RANGE, "",
4410 name ? name : "null", value, min, max);
4411 return;
4414 env->cpuid_version &= ~0xf00f0;
4415 env->cpuid_version |= ((value & 0xf) << 4) | ((value >> 4) << 16);
4418 static void x86_cpuid_version_get_stepping(Object *obj, Visitor *v,
4419 const char *name, void *opaque,
4420 Error **errp)
4422 X86CPU *cpu = X86_CPU(obj);
4423 CPUX86State *env = &cpu->env;
4424 int64_t value;
4426 value = env->cpuid_version & 0xf;
4427 visit_type_int(v, name, &value, errp);
4430 static void x86_cpuid_version_set_stepping(Object *obj, Visitor *v,
4431 const char *name, void *opaque,
4432 Error **errp)
4434 X86CPU *cpu = X86_CPU(obj);
4435 CPUX86State *env = &cpu->env;
4436 const int64_t min = 0;
4437 const int64_t max = 0xf;
4438 int64_t value;
4440 if (!visit_type_int(v, name, &value, errp)) {
4441 return;
4443 if (value < min || value > max) {
4444 error_setg(errp, QERR_PROPERTY_VALUE_OUT_OF_RANGE, "",
4445 name ? name : "null", value, min, max);
4446 return;
4449 env->cpuid_version &= ~0xf;
4450 env->cpuid_version |= value & 0xf;
4453 static char *x86_cpuid_get_vendor(Object *obj, Error **errp)
4455 X86CPU *cpu = X86_CPU(obj);
4456 CPUX86State *env = &cpu->env;
4457 char *value;
4459 value = g_malloc(CPUID_VENDOR_SZ + 1);
4460 x86_cpu_vendor_words2str(value, env->cpuid_vendor1, env->cpuid_vendor2,
4461 env->cpuid_vendor3);
4462 return value;
4465 static void x86_cpuid_set_vendor(Object *obj, const char *value,
4466 Error **errp)
4468 X86CPU *cpu = X86_CPU(obj);
4469 CPUX86State *env = &cpu->env;
4470 int i;
4472 if (strlen(value) != CPUID_VENDOR_SZ) {
4473 error_setg(errp, QERR_PROPERTY_VALUE_BAD, "", "vendor", value);
4474 return;
4477 env->cpuid_vendor1 = 0;
4478 env->cpuid_vendor2 = 0;
4479 env->cpuid_vendor3 = 0;
4480 for (i = 0; i < 4; i++) {
4481 env->cpuid_vendor1 |= ((uint8_t)value[i ]) << (8 * i);
4482 env->cpuid_vendor2 |= ((uint8_t)value[i + 4]) << (8 * i);
4483 env->cpuid_vendor3 |= ((uint8_t)value[i + 8]) << (8 * i);
4487 static char *x86_cpuid_get_model_id(Object *obj, Error **errp)
4489 X86CPU *cpu = X86_CPU(obj);
4490 CPUX86State *env = &cpu->env;
4491 char *value;
4492 int i;
4494 value = g_malloc(48 + 1);
4495 for (i = 0; i < 48; i++) {
4496 value[i] = env->cpuid_model[i >> 2] >> (8 * (i & 3));
4498 value[48] = '\0';
4499 return value;
4502 static void x86_cpuid_set_model_id(Object *obj, const char *model_id,
4503 Error **errp)
4505 X86CPU *cpu = X86_CPU(obj);
4506 CPUX86State *env = &cpu->env;
4507 int c, len, i;
4509 if (model_id == NULL) {
4510 model_id = "";
4512 len = strlen(model_id);
4513 memset(env->cpuid_model, 0, 48);
4514 for (i = 0; i < 48; i++) {
4515 if (i >= len) {
4516 c = '\0';
4517 } else {
4518 c = (uint8_t)model_id[i];
4520 env->cpuid_model[i >> 2] |= c << (8 * (i & 3));
4524 static void x86_cpuid_get_tsc_freq(Object *obj, Visitor *v, const char *name,
4525 void *opaque, Error **errp)
4527 X86CPU *cpu = X86_CPU(obj);
4528 int64_t value;
4530 value = cpu->env.tsc_khz * 1000;
4531 visit_type_int(v, name, &value, errp);
4534 static void x86_cpuid_set_tsc_freq(Object *obj, Visitor *v, const char *name,
4535 void *opaque, Error **errp)
4537 X86CPU *cpu = X86_CPU(obj);
4538 const int64_t min = 0;
4539 const int64_t max = INT64_MAX;
4540 int64_t value;
4542 if (!visit_type_int(v, name, &value, errp)) {
4543 return;
4545 if (value < min || value > max) {
4546 error_setg(errp, QERR_PROPERTY_VALUE_OUT_OF_RANGE, "",
4547 name ? name : "null", value, min, max);
4548 return;
4551 cpu->env.tsc_khz = cpu->env.user_tsc_khz = value / 1000;
4554 /* Generic getter for "feature-words" and "filtered-features" properties */
4555 static void x86_cpu_get_feature_words(Object *obj, Visitor *v,
4556 const char *name, void *opaque,
4557 Error **errp)
4559 uint64_t *array = (uint64_t *)opaque;
4560 FeatureWord w;
4561 X86CPUFeatureWordInfo word_infos[FEATURE_WORDS] = { };
4562 X86CPUFeatureWordInfoList list_entries[FEATURE_WORDS] = { };
4563 X86CPUFeatureWordInfoList *list = NULL;
4565 for (w = 0; w < FEATURE_WORDS; w++) {
4566 FeatureWordInfo *wi = &feature_word_info[w];
4568 * We didn't have MSR features when "feature-words" was
4569 * introduced. Therefore skipped other type entries.
4571 if (wi->type != CPUID_FEATURE_WORD) {
4572 continue;
4574 X86CPUFeatureWordInfo *qwi = &word_infos[w];
4575 qwi->cpuid_input_eax = wi->cpuid.eax;
4576 qwi->has_cpuid_input_ecx = wi->cpuid.needs_ecx;
4577 qwi->cpuid_input_ecx = wi->cpuid.ecx;
4578 qwi->cpuid_register = x86_reg_info_32[wi->cpuid.reg].qapi_enum;
4579 qwi->features = array[w];
4581 /* List will be in reverse order, but order shouldn't matter */
4582 list_entries[w].next = list;
4583 list_entries[w].value = &word_infos[w];
4584 list = &list_entries[w];
4587 visit_type_X86CPUFeatureWordInfoList(v, "feature-words", &list, errp);
4590 /* Convert all '_' in a feature string option name to '-', to make feature
4591 * name conform to QOM property naming rule, which uses '-' instead of '_'.
4593 static inline void feat2prop(char *s)
4595 while ((s = strchr(s, '_'))) {
4596 *s = '-';
4600 /* Return the feature property name for a feature flag bit */
4601 static const char *x86_cpu_feature_name(FeatureWord w, int bitnr)
4603 const char *name;
4604 /* XSAVE components are automatically enabled by other features,
4605 * so return the original feature name instead
4607 if (w == FEAT_XSAVE_COMP_LO || w == FEAT_XSAVE_COMP_HI) {
4608 int comp = (w == FEAT_XSAVE_COMP_HI) ? bitnr + 32 : bitnr;
4610 if (comp < ARRAY_SIZE(x86_ext_save_areas) &&
4611 x86_ext_save_areas[comp].bits) {
4612 w = x86_ext_save_areas[comp].feature;
4613 bitnr = ctz32(x86_ext_save_areas[comp].bits);
4617 assert(bitnr < 64);
4618 assert(w < FEATURE_WORDS);
4619 name = feature_word_info[w].feat_names[bitnr];
4620 assert(bitnr < 32 || !(name && feature_word_info[w].type == CPUID_FEATURE_WORD));
4621 return name;
4624 /* Compatibily hack to maintain legacy +-feat semantic,
4625 * where +-feat overwrites any feature set by
4626 * feat=on|feat even if the later is parsed after +-feat
4627 * (i.e. "-x2apic,x2apic=on" will result in x2apic disabled)
4629 static GList *plus_features, *minus_features;
4631 static gint compare_string(gconstpointer a, gconstpointer b)
4633 return g_strcmp0(a, b);
4636 /* Parse "+feature,-feature,feature=foo" CPU feature string
4638 static void x86_cpu_parse_featurestr(const char *typename, char *features,
4639 Error **errp)
4641 char *featurestr; /* Single 'key=value" string being parsed */
4642 static bool cpu_globals_initialized;
4643 bool ambiguous = false;
4645 if (cpu_globals_initialized) {
4646 return;
4648 cpu_globals_initialized = true;
4650 if (!features) {
4651 return;
4654 for (featurestr = strtok(features, ",");
4655 featurestr;
4656 featurestr = strtok(NULL, ",")) {
4657 const char *name;
4658 const char *val = NULL;
4659 char *eq = NULL;
4660 char num[32];
4661 GlobalProperty *prop;
4663 /* Compatibility syntax: */
4664 if (featurestr[0] == '+') {
4665 plus_features = g_list_append(plus_features,
4666 g_strdup(featurestr + 1));
4667 continue;
4668 } else if (featurestr[0] == '-') {
4669 minus_features = g_list_append(minus_features,
4670 g_strdup(featurestr + 1));
4671 continue;
4674 eq = strchr(featurestr, '=');
4675 if (eq) {
4676 *eq++ = 0;
4677 val = eq;
4678 } else {
4679 val = "on";
4682 feat2prop(featurestr);
4683 name = featurestr;
4685 if (g_list_find_custom(plus_features, name, compare_string)) {
4686 warn_report("Ambiguous CPU model string. "
4687 "Don't mix both \"+%s\" and \"%s=%s\"",
4688 name, name, val);
4689 ambiguous = true;
4691 if (g_list_find_custom(minus_features, name, compare_string)) {
4692 warn_report("Ambiguous CPU model string. "
4693 "Don't mix both \"-%s\" and \"%s=%s\"",
4694 name, name, val);
4695 ambiguous = true;
4698 /* Special case: */
4699 if (!strcmp(name, "tsc-freq")) {
4700 int ret;
4701 uint64_t tsc_freq;
4703 ret = qemu_strtosz_metric(val, NULL, &tsc_freq);
4704 if (ret < 0 || tsc_freq > INT64_MAX) {
4705 error_setg(errp, "bad numerical value %s", val);
4706 return;
4708 snprintf(num, sizeof(num), "%" PRId64, tsc_freq);
4709 val = num;
4710 name = "tsc-frequency";
4713 prop = g_new0(typeof(*prop), 1);
4714 prop->driver = typename;
4715 prop->property = g_strdup(name);
4716 prop->value = g_strdup(val);
4717 qdev_prop_register_global(prop);
4720 if (ambiguous) {
4721 warn_report("Compatibility of ambiguous CPU model "
4722 "strings won't be kept on future QEMU versions");
4726 static void x86_cpu_filter_features(X86CPU *cpu, bool verbose);
4728 /* Build a list with the name of all features on a feature word array */
4729 static void x86_cpu_list_feature_names(FeatureWordArray features,
4730 strList **list)
4732 strList **tail = list;
4733 FeatureWord w;
4735 for (w = 0; w < FEATURE_WORDS; w++) {
4736 uint64_t filtered = features[w];
4737 int i;
4738 for (i = 0; i < 64; i++) {
4739 if (filtered & (1ULL << i)) {
4740 QAPI_LIST_APPEND(tail, g_strdup(x86_cpu_feature_name(w, i)));
4746 static void x86_cpu_get_unavailable_features(Object *obj, Visitor *v,
4747 const char *name, void *opaque,
4748 Error **errp)
4750 X86CPU *xc = X86_CPU(obj);
4751 strList *result = NULL;
4753 x86_cpu_list_feature_names(xc->filtered_features, &result);
4754 visit_type_strList(v, "unavailable-features", &result, errp);
4757 /* Check for missing features that may prevent the CPU class from
4758 * running using the current machine and accelerator.
4760 static void x86_cpu_class_check_missing_features(X86CPUClass *xcc,
4761 strList **list)
4763 strList **tail = list;
4764 X86CPU *xc;
4765 Error *err = NULL;
4767 if (xcc->host_cpuid_required && !accel_uses_host_cpuid()) {
4768 QAPI_LIST_APPEND(tail, g_strdup("kvm"));
4769 return;
4772 xc = X86_CPU(object_new_with_class(OBJECT_CLASS(xcc)));
4774 x86_cpu_expand_features(xc, &err);
4775 if (err) {
4776 /* Errors at x86_cpu_expand_features should never happen,
4777 * but in case it does, just report the model as not
4778 * runnable at all using the "type" property.
4780 QAPI_LIST_APPEND(tail, g_strdup("type"));
4781 error_free(err);
4784 x86_cpu_filter_features(xc, false);
4786 x86_cpu_list_feature_names(xc->filtered_features, tail);
4788 object_unref(OBJECT(xc));
4791 /* Print all cpuid feature names in featureset
4793 static void listflags(GList *features)
4795 size_t len = 0;
4796 GList *tmp;
4798 for (tmp = features; tmp; tmp = tmp->next) {
4799 const char *name = tmp->data;
4800 if ((len + strlen(name) + 1) >= 75) {
4801 qemu_printf("\n");
4802 len = 0;
4804 qemu_printf("%s%s", len == 0 ? " " : " ", name);
4805 len += strlen(name) + 1;
4807 qemu_printf("\n");
4810 /* Sort alphabetically by type name, respecting X86CPUClass::ordering. */
4811 static gint x86_cpu_list_compare(gconstpointer a, gconstpointer b)
4813 ObjectClass *class_a = (ObjectClass *)a;
4814 ObjectClass *class_b = (ObjectClass *)b;
4815 X86CPUClass *cc_a = X86_CPU_CLASS(class_a);
4816 X86CPUClass *cc_b = X86_CPU_CLASS(class_b);
4817 int ret;
4819 if (cc_a->ordering != cc_b->ordering) {
4820 ret = cc_a->ordering - cc_b->ordering;
4821 } else {
4822 g_autofree char *name_a = x86_cpu_class_get_model_name(cc_a);
4823 g_autofree char *name_b = x86_cpu_class_get_model_name(cc_b);
4824 ret = strcmp(name_a, name_b);
4826 return ret;
4829 static GSList *get_sorted_cpu_model_list(void)
4831 GSList *list = object_class_get_list(TYPE_X86_CPU, false);
4832 list = g_slist_sort(list, x86_cpu_list_compare);
4833 return list;
4836 static char *x86_cpu_class_get_model_id(X86CPUClass *xc)
4838 Object *obj = object_new_with_class(OBJECT_CLASS(xc));
4839 char *r = object_property_get_str(obj, "model-id", &error_abort);
4840 object_unref(obj);
4841 return r;
4844 static char *x86_cpu_class_get_alias_of(X86CPUClass *cc)
4846 X86CPUVersion version;
4848 if (!cc->model || !cc->model->is_alias) {
4849 return NULL;
4851 version = x86_cpu_model_resolve_version(cc->model);
4852 if (version <= 0) {
4853 return NULL;
4855 return x86_cpu_versioned_model_name(cc->model->cpudef, version);
4858 static void x86_cpu_list_entry(gpointer data, gpointer user_data)
4860 ObjectClass *oc = data;
4861 X86CPUClass *cc = X86_CPU_CLASS(oc);
4862 g_autofree char *name = x86_cpu_class_get_model_name(cc);
4863 g_autofree char *desc = g_strdup(cc->model_description);
4864 g_autofree char *alias_of = x86_cpu_class_get_alias_of(cc);
4865 g_autofree char *model_id = x86_cpu_class_get_model_id(cc);
4867 if (!desc && alias_of) {
4868 if (cc->model && cc->model->version == CPU_VERSION_AUTO) {
4869 desc = g_strdup("(alias configured by machine type)");
4870 } else {
4871 desc = g_strdup_printf("(alias of %s)", alias_of);
4874 if (!desc && cc->model && cc->model->note) {
4875 desc = g_strdup_printf("%s [%s]", model_id, cc->model->note);
4877 if (!desc) {
4878 desc = g_strdup_printf("%s", model_id);
4881 qemu_printf("x86 %-20s %s\n", name, desc);
4884 /* list available CPU models and flags */
4885 void x86_cpu_list(void)
4887 int i, j;
4888 GSList *list;
4889 GList *names = NULL;
4891 qemu_printf("Available CPUs:\n");
4892 list = get_sorted_cpu_model_list();
4893 g_slist_foreach(list, x86_cpu_list_entry, NULL);
4894 g_slist_free(list);
4896 names = NULL;
4897 for (i = 0; i < ARRAY_SIZE(feature_word_info); i++) {
4898 FeatureWordInfo *fw = &feature_word_info[i];
4899 for (j = 0; j < 64; j++) {
4900 if (fw->feat_names[j]) {
4901 names = g_list_append(names, (gpointer)fw->feat_names[j]);
4906 names = g_list_sort(names, (GCompareFunc)strcmp);
4908 qemu_printf("\nRecognized CPUID flags:\n");
4909 listflags(names);
4910 qemu_printf("\n");
4911 g_list_free(names);
4914 static void x86_cpu_definition_entry(gpointer data, gpointer user_data)
4916 ObjectClass *oc = data;
4917 X86CPUClass *cc = X86_CPU_CLASS(oc);
4918 CpuDefinitionInfoList **cpu_list = user_data;
4919 CpuDefinitionInfo *info;
4921 info = g_malloc0(sizeof(*info));
4922 info->name = x86_cpu_class_get_model_name(cc);
4923 x86_cpu_class_check_missing_features(cc, &info->unavailable_features);
4924 info->has_unavailable_features = true;
4925 info->q_typename = g_strdup(object_class_get_name(oc));
4926 info->migration_safe = cc->migration_safe;
4927 info->has_migration_safe = true;
4928 info->q_static = cc->static_model;
4929 if (cc->model && cc->model->cpudef->deprecation_note) {
4930 info->deprecated = true;
4931 } else {
4932 info->deprecated = false;
4935 * Old machine types won't report aliases, so that alias translation
4936 * doesn't break compatibility with previous QEMU versions.
4938 if (default_cpu_version != CPU_VERSION_LEGACY) {
4939 info->alias_of = x86_cpu_class_get_alias_of(cc);
4940 info->has_alias_of = !!info->alias_of;
4943 QAPI_LIST_PREPEND(*cpu_list, info);
4946 CpuDefinitionInfoList *qmp_query_cpu_definitions(Error **errp)
4948 CpuDefinitionInfoList *cpu_list = NULL;
4949 GSList *list = get_sorted_cpu_model_list();
4950 g_slist_foreach(list, x86_cpu_definition_entry, &cpu_list);
4951 g_slist_free(list);
4952 return cpu_list;
4955 static uint64_t x86_cpu_get_supported_feature_word(FeatureWord w,
4956 bool migratable_only)
4958 FeatureWordInfo *wi = &feature_word_info[w];
4959 uint64_t r = 0;
4961 if (kvm_enabled()) {
4962 switch (wi->type) {
4963 case CPUID_FEATURE_WORD:
4964 r = kvm_arch_get_supported_cpuid(kvm_state, wi->cpuid.eax,
4965 wi->cpuid.ecx,
4966 wi->cpuid.reg);
4967 break;
4968 case MSR_FEATURE_WORD:
4969 r = kvm_arch_get_supported_msr_feature(kvm_state,
4970 wi->msr.index);
4971 break;
4973 } else if (hvf_enabled()) {
4974 if (wi->type != CPUID_FEATURE_WORD) {
4975 return 0;
4977 r = hvf_get_supported_cpuid(wi->cpuid.eax,
4978 wi->cpuid.ecx,
4979 wi->cpuid.reg);
4980 } else if (tcg_enabled()) {
4981 r = wi->tcg_features;
4982 } else {
4983 return ~0;
4985 #ifndef TARGET_X86_64
4986 if (w == FEAT_8000_0001_EDX) {
4987 r &= ~CPUID_EXT2_LM;
4989 #endif
4990 if (migratable_only) {
4991 r &= x86_cpu_get_migratable_flags(w);
4993 return r;
4997 * Only for builtin_x86_defs models initialized with x86_register_cpudef_types.
4999 void x86_cpu_apply_props(X86CPU *cpu, PropValue *props)
5001 PropValue *pv;
5002 for (pv = props; pv->prop; pv++) {
5003 if (!pv->value) {
5004 continue;
5006 object_property_parse(OBJECT(cpu), pv->prop, pv->value,
5007 &error_abort);
5012 * Apply properties for the CPU model version specified in model.
5013 * Only for builtin_x86_defs models initialized with x86_register_cpudef_types.
5016 static void x86_cpu_apply_version_props(X86CPU *cpu, X86CPUModel *model)
5018 const X86CPUVersionDefinition *vdef;
5019 X86CPUVersion version = x86_cpu_model_resolve_version(model);
5021 if (version == CPU_VERSION_LEGACY) {
5022 return;
5025 for (vdef = x86_cpu_def_get_versions(model->cpudef); vdef->version; vdef++) {
5026 PropValue *p;
5028 for (p = vdef->props; p && p->prop; p++) {
5029 object_property_parse(OBJECT(cpu), p->prop, p->value,
5030 &error_abort);
5033 if (vdef->version == version) {
5034 break;
5039 * If we reached the end of the list, version number was invalid
5041 assert(vdef->version == version);
5045 * Load data from X86CPUDefinition into a X86CPU object.
5046 * Only for builtin_x86_defs models initialized with x86_register_cpudef_types.
5048 static void x86_cpu_load_model(X86CPU *cpu, X86CPUModel *model)
5050 const X86CPUDefinition *def = model->cpudef;
5051 CPUX86State *env = &cpu->env;
5052 FeatureWord w;
5054 /*NOTE: any property set by this function should be returned by
5055 * x86_cpu_static_props(), so static expansion of
5056 * query-cpu-model-expansion is always complete.
5059 /* CPU models only set _minimum_ values for level/xlevel: */
5060 object_property_set_uint(OBJECT(cpu), "min-level", def->level,
5061 &error_abort);
5062 object_property_set_uint(OBJECT(cpu), "min-xlevel", def->xlevel,
5063 &error_abort);
5065 object_property_set_int(OBJECT(cpu), "family", def->family, &error_abort);
5066 object_property_set_int(OBJECT(cpu), "model", def->model, &error_abort);
5067 object_property_set_int(OBJECT(cpu), "stepping", def->stepping,
5068 &error_abort);
5069 object_property_set_str(OBJECT(cpu), "model-id", def->model_id,
5070 &error_abort);
5071 for (w = 0; w < FEATURE_WORDS; w++) {
5072 env->features[w] = def->features[w];
5075 /* legacy-cache defaults to 'off' if CPU model provides cache info */
5076 cpu->legacy_cache = !def->cache_info;
5078 env->features[FEAT_1_ECX] |= CPUID_EXT_HYPERVISOR;
5080 /* sysenter isn't supported in compatibility mode on AMD,
5081 * syscall isn't supported in compatibility mode on Intel.
5082 * Normally we advertise the actual CPU vendor, but you can
5083 * override this using the 'vendor' property if you want to use
5084 * KVM's sysenter/syscall emulation in compatibility mode and
5085 * when doing cross vendor migration
5089 * vendor property is set here but then overloaded with the
5090 * host cpu vendor for KVM and HVF.
5092 object_property_set_str(OBJECT(cpu), "vendor", def->vendor, &error_abort);
5094 x86_cpu_apply_version_props(cpu, model);
5097 * Properties in versioned CPU model are not user specified features.
5098 * We can simply clear env->user_features here since it will be filled later
5099 * in x86_cpu_expand_features() based on plus_features and minus_features.
5101 memset(&env->user_features, 0, sizeof(env->user_features));
5104 static gchar *x86_gdb_arch_name(CPUState *cs)
5106 #ifdef TARGET_X86_64
5107 return g_strdup("i386:x86-64");
5108 #else
5109 return g_strdup("i386");
5110 #endif
5113 static void x86_cpu_cpudef_class_init(ObjectClass *oc, void *data)
5115 X86CPUModel *model = data;
5116 X86CPUClass *xcc = X86_CPU_CLASS(oc);
5117 CPUClass *cc = CPU_CLASS(oc);
5119 xcc->model = model;
5120 xcc->migration_safe = true;
5121 cc->deprecation_note = model->cpudef->deprecation_note;
5124 static void x86_register_cpu_model_type(const char *name, X86CPUModel *model)
5126 g_autofree char *typename = x86_cpu_type_name(name);
5127 TypeInfo ti = {
5128 .name = typename,
5129 .parent = TYPE_X86_CPU,
5130 .class_init = x86_cpu_cpudef_class_init,
5131 .class_data = model,
5134 type_register(&ti);
5139 * register builtin_x86_defs;
5140 * "max", "base" and subclasses ("host") are not registered here.
5141 * See x86_cpu_register_types for all model registrations.
5143 static void x86_register_cpudef_types(const X86CPUDefinition *def)
5145 X86CPUModel *m;
5146 const X86CPUVersionDefinition *vdef;
5148 /* AMD aliases are handled at runtime based on CPUID vendor, so
5149 * they shouldn't be set on the CPU model table.
5151 assert(!(def->features[FEAT_8000_0001_EDX] & CPUID_EXT2_AMD_ALIASES));
5152 /* catch mistakes instead of silently truncating model_id when too long */
5153 assert(def->model_id && strlen(def->model_id) <= 48);
5155 /* Unversioned model: */
5156 m = g_new0(X86CPUModel, 1);
5157 m->cpudef = def;
5158 m->version = CPU_VERSION_AUTO;
5159 m->is_alias = true;
5160 x86_register_cpu_model_type(def->name, m);
5162 /* Versioned models: */
5164 for (vdef = x86_cpu_def_get_versions(def); vdef->version; vdef++) {
5165 X86CPUModel *m = g_new0(X86CPUModel, 1);
5166 g_autofree char *name =
5167 x86_cpu_versioned_model_name(def, vdef->version);
5168 m->cpudef = def;
5169 m->version = vdef->version;
5170 m->note = vdef->note;
5171 x86_register_cpu_model_type(name, m);
5173 if (vdef->alias) {
5174 X86CPUModel *am = g_new0(X86CPUModel, 1);
5175 am->cpudef = def;
5176 am->version = vdef->version;
5177 am->is_alias = true;
5178 x86_register_cpu_model_type(vdef->alias, am);
5184 uint32_t cpu_x86_virtual_addr_width(CPUX86State *env)
5186 if (env->features[FEAT_7_0_ECX] & CPUID_7_0_ECX_LA57) {
5187 return 57; /* 57 bits virtual */
5188 } else {
5189 return 48; /* 48 bits virtual */
5193 void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count,
5194 uint32_t *eax, uint32_t *ebx,
5195 uint32_t *ecx, uint32_t *edx)
5197 X86CPU *cpu = env_archcpu(env);
5198 CPUState *cs = env_cpu(env);
5199 uint32_t die_offset;
5200 uint32_t limit;
5201 uint32_t signature[3];
5202 X86CPUTopoInfo topo_info;
5204 topo_info.dies_per_pkg = env->nr_dies;
5205 topo_info.cores_per_die = cs->nr_cores;
5206 topo_info.threads_per_core = cs->nr_threads;
5208 /* Calculate & apply limits for different index ranges */
5209 if (index >= 0xC0000000) {
5210 limit = env->cpuid_xlevel2;
5211 } else if (index >= 0x80000000) {
5212 limit = env->cpuid_xlevel;
5213 } else if (index >= 0x40000000) {
5214 limit = 0x40000001;
5215 } else {
5216 limit = env->cpuid_level;
5219 if (index > limit) {
5220 /* Intel documentation states that invalid EAX input will
5221 * return the same information as EAX=cpuid_level
5222 * (Intel SDM Vol. 2A - Instruction Set Reference - CPUID)
5224 index = env->cpuid_level;
5227 switch(index) {
5228 case 0:
5229 *eax = env->cpuid_level;
5230 *ebx = env->cpuid_vendor1;
5231 *edx = env->cpuid_vendor2;
5232 *ecx = env->cpuid_vendor3;
5233 break;
5234 case 1:
5235 *eax = env->cpuid_version;
5236 *ebx = (cpu->apic_id << 24) |
5237 8 << 8; /* CLFLUSH size in quad words, Linux wants it. */
5238 *ecx = env->features[FEAT_1_ECX];
5239 if ((*ecx & CPUID_EXT_XSAVE) && (env->cr[4] & CR4_OSXSAVE_MASK)) {
5240 *ecx |= CPUID_EXT_OSXSAVE;
5242 *edx = env->features[FEAT_1_EDX];
5243 if (cs->nr_cores * cs->nr_threads > 1) {
5244 *ebx |= (cs->nr_cores * cs->nr_threads) << 16;
5245 *edx |= CPUID_HT;
5247 if (!cpu->enable_pmu) {
5248 *ecx &= ~CPUID_EXT_PDCM;
5250 break;
5251 case 2:
5252 /* cache info: needed for Pentium Pro compatibility */
5253 if (cpu->cache_info_passthrough) {
5254 host_cpuid(index, 0, eax, ebx, ecx, edx);
5255 break;
5256 } else if (cpu->vendor_cpuid_only && IS_AMD_CPU(env)) {
5257 *eax = *ebx = *ecx = *edx = 0;
5258 break;
5260 *eax = 1; /* Number of CPUID[EAX=2] calls required */
5261 *ebx = 0;
5262 if (!cpu->enable_l3_cache) {
5263 *ecx = 0;
5264 } else {
5265 *ecx = cpuid2_cache_descriptor(env->cache_info_cpuid2.l3_cache);
5267 *edx = (cpuid2_cache_descriptor(env->cache_info_cpuid2.l1d_cache) << 16) |
5268 (cpuid2_cache_descriptor(env->cache_info_cpuid2.l1i_cache) << 8) |
5269 (cpuid2_cache_descriptor(env->cache_info_cpuid2.l2_cache));
5270 break;
5271 case 4:
5272 /* cache info: needed for Core compatibility */
5273 if (cpu->cache_info_passthrough) {
5274 host_cpuid(index, count, eax, ebx, ecx, edx);
5275 /* QEMU gives out its own APIC IDs, never pass down bits 31..26. */
5276 *eax &= ~0xFC000000;
5277 if ((*eax & 31) && cs->nr_cores > 1) {
5278 *eax |= (cs->nr_cores - 1) << 26;
5280 } else if (cpu->vendor_cpuid_only && IS_AMD_CPU(env)) {
5281 *eax = *ebx = *ecx = *edx = 0;
5282 } else {
5283 *eax = 0;
5284 switch (count) {
5285 case 0: /* L1 dcache info */
5286 encode_cache_cpuid4(env->cache_info_cpuid4.l1d_cache,
5287 1, cs->nr_cores,
5288 eax, ebx, ecx, edx);
5289 break;
5290 case 1: /* L1 icache info */
5291 encode_cache_cpuid4(env->cache_info_cpuid4.l1i_cache,
5292 1, cs->nr_cores,
5293 eax, ebx, ecx, edx);
5294 break;
5295 case 2: /* L2 cache info */
5296 encode_cache_cpuid4(env->cache_info_cpuid4.l2_cache,
5297 cs->nr_threads, cs->nr_cores,
5298 eax, ebx, ecx, edx);
5299 break;
5300 case 3: /* L3 cache info */
5301 die_offset = apicid_die_offset(&topo_info);
5302 if (cpu->enable_l3_cache) {
5303 encode_cache_cpuid4(env->cache_info_cpuid4.l3_cache,
5304 (1 << die_offset), cs->nr_cores,
5305 eax, ebx, ecx, edx);
5306 break;
5308 /* fall through */
5309 default: /* end of info */
5310 *eax = *ebx = *ecx = *edx = 0;
5311 break;
5314 break;
5315 case 5:
5316 /* MONITOR/MWAIT Leaf */
5317 *eax = cpu->mwait.eax; /* Smallest monitor-line size in bytes */
5318 *ebx = cpu->mwait.ebx; /* Largest monitor-line size in bytes */
5319 *ecx = cpu->mwait.ecx; /* flags */
5320 *edx = cpu->mwait.edx; /* mwait substates */
5321 break;
5322 case 6:
5323 /* Thermal and Power Leaf */
5324 *eax = env->features[FEAT_6_EAX];
5325 *ebx = 0;
5326 *ecx = 0;
5327 *edx = 0;
5328 break;
5329 case 7:
5330 /* Structured Extended Feature Flags Enumeration Leaf */
5331 if (count == 0) {
5332 /* Maximum ECX value for sub-leaves */
5333 *eax = env->cpuid_level_func7;
5334 *ebx = env->features[FEAT_7_0_EBX]; /* Feature flags */
5335 *ecx = env->features[FEAT_7_0_ECX]; /* Feature flags */
5336 if ((*ecx & CPUID_7_0_ECX_PKU) && env->cr[4] & CR4_PKE_MASK) {
5337 *ecx |= CPUID_7_0_ECX_OSPKE;
5339 *edx = env->features[FEAT_7_0_EDX]; /* Feature flags */
5342 * SGX cannot be emulated in software. If hardware does not
5343 * support enabling SGX and/or SGX flexible launch control,
5344 * then we need to update the VM's CPUID values accordingly.
5346 if ((*ebx & CPUID_7_0_EBX_SGX) &&
5347 (!kvm_enabled() ||
5348 !(kvm_arch_get_supported_cpuid(cs->kvm_state, 0x7, 0, R_EBX) &
5349 CPUID_7_0_EBX_SGX))) {
5350 *ebx &= ~CPUID_7_0_EBX_SGX;
5353 if ((*ecx & CPUID_7_0_ECX_SGX_LC) &&
5354 (!(*ebx & CPUID_7_0_EBX_SGX) || !kvm_enabled() ||
5355 !(kvm_arch_get_supported_cpuid(cs->kvm_state, 0x7, 0, R_ECX) &
5356 CPUID_7_0_ECX_SGX_LC))) {
5357 *ecx &= ~CPUID_7_0_ECX_SGX_LC;
5359 } else if (count == 1) {
5360 *eax = env->features[FEAT_7_1_EAX];
5361 *ebx = 0;
5362 *ecx = 0;
5363 *edx = 0;
5364 } else {
5365 *eax = 0;
5366 *ebx = 0;
5367 *ecx = 0;
5368 *edx = 0;
5370 break;
5371 case 9:
5372 /* Direct Cache Access Information Leaf */
5373 *eax = 0; /* Bits 0-31 in DCA_CAP MSR */
5374 *ebx = 0;
5375 *ecx = 0;
5376 *edx = 0;
5377 break;
5378 case 0xA:
5379 /* Architectural Performance Monitoring Leaf */
5380 if (kvm_enabled() && cpu->enable_pmu) {
5381 KVMState *s = cs->kvm_state;
5383 *eax = kvm_arch_get_supported_cpuid(s, 0xA, count, R_EAX);
5384 *ebx = kvm_arch_get_supported_cpuid(s, 0xA, count, R_EBX);
5385 *ecx = kvm_arch_get_supported_cpuid(s, 0xA, count, R_ECX);
5386 *edx = kvm_arch_get_supported_cpuid(s, 0xA, count, R_EDX);
5387 } else if (hvf_enabled() && cpu->enable_pmu) {
5388 *eax = hvf_get_supported_cpuid(0xA, count, R_EAX);
5389 *ebx = hvf_get_supported_cpuid(0xA, count, R_EBX);
5390 *ecx = hvf_get_supported_cpuid(0xA, count, R_ECX);
5391 *edx = hvf_get_supported_cpuid(0xA, count, R_EDX);
5392 } else {
5393 *eax = 0;
5394 *ebx = 0;
5395 *ecx = 0;
5396 *edx = 0;
5398 break;
5399 case 0xB:
5400 /* Extended Topology Enumeration Leaf */
5401 if (!cpu->enable_cpuid_0xb) {
5402 *eax = *ebx = *ecx = *edx = 0;
5403 break;
5406 *ecx = count & 0xff;
5407 *edx = cpu->apic_id;
5409 switch (count) {
5410 case 0:
5411 *eax = apicid_core_offset(&topo_info);
5412 *ebx = cs->nr_threads;
5413 *ecx |= CPUID_TOPOLOGY_LEVEL_SMT;
5414 break;
5415 case 1:
5416 *eax = apicid_pkg_offset(&topo_info);
5417 *ebx = cs->nr_cores * cs->nr_threads;
5418 *ecx |= CPUID_TOPOLOGY_LEVEL_CORE;
5419 break;
5420 default:
5421 *eax = 0;
5422 *ebx = 0;
5423 *ecx |= CPUID_TOPOLOGY_LEVEL_INVALID;
5426 assert(!(*eax & ~0x1f));
5427 *ebx &= 0xffff; /* The count doesn't need to be reliable. */
5428 break;
5429 case 0x1F:
5430 /* V2 Extended Topology Enumeration Leaf */
5431 if (env->nr_dies < 2) {
5432 *eax = *ebx = *ecx = *edx = 0;
5433 break;
5436 *ecx = count & 0xff;
5437 *edx = cpu->apic_id;
5438 switch (count) {
5439 case 0:
5440 *eax = apicid_core_offset(&topo_info);
5441 *ebx = cs->nr_threads;
5442 *ecx |= CPUID_TOPOLOGY_LEVEL_SMT;
5443 break;
5444 case 1:
5445 *eax = apicid_die_offset(&topo_info);
5446 *ebx = cs->nr_cores * cs->nr_threads;
5447 *ecx |= CPUID_TOPOLOGY_LEVEL_CORE;
5448 break;
5449 case 2:
5450 *eax = apicid_pkg_offset(&topo_info);
5451 *ebx = env->nr_dies * cs->nr_cores * cs->nr_threads;
5452 *ecx |= CPUID_TOPOLOGY_LEVEL_DIE;
5453 break;
5454 default:
5455 *eax = 0;
5456 *ebx = 0;
5457 *ecx |= CPUID_TOPOLOGY_LEVEL_INVALID;
5459 assert(!(*eax & ~0x1f));
5460 *ebx &= 0xffff; /* The count doesn't need to be reliable. */
5461 break;
5462 case 0xD: {
5463 /* Processor Extended State */
5464 *eax = 0;
5465 *ebx = 0;
5466 *ecx = 0;
5467 *edx = 0;
5468 if (!(env->features[FEAT_1_ECX] & CPUID_EXT_XSAVE)) {
5469 break;
5472 if (count == 0) {
5473 *ecx = xsave_area_size(x86_cpu_xsave_components(cpu));
5474 *eax = env->features[FEAT_XSAVE_COMP_LO];
5475 *edx = env->features[FEAT_XSAVE_COMP_HI];
5477 * The initial value of xcr0 and ebx == 0, On host without kvm
5478 * commit 412a3c41(e.g., CentOS 6), the ebx's value always == 0
5479 * even through guest update xcr0, this will crash some legacy guest
5480 * (e.g., CentOS 6), So set ebx == ecx to workaroud it.
5482 *ebx = kvm_enabled() ? *ecx : xsave_area_size(env->xcr0);
5483 } else if (count == 1) {
5484 *eax = env->features[FEAT_XSAVE];
5485 } else if (count < ARRAY_SIZE(x86_ext_save_areas)) {
5486 if ((x86_cpu_xsave_components(cpu) >> count) & 1) {
5487 const ExtSaveArea *esa = &x86_ext_save_areas[count];
5488 *eax = esa->size;
5489 *ebx = esa->offset;
5492 break;
5494 case 0x12:
5495 #ifndef CONFIG_USER_ONLY
5496 if (!kvm_enabled() ||
5497 !(env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_SGX)) {
5498 *eax = *ebx = *ecx = *edx = 0;
5499 break;
5503 * SGX sub-leafs CPUID.0x12.{0x2..N} enumerate EPC sections. Retrieve
5504 * the EPC properties, e.g. confidentiality and integrity, from the
5505 * host's first EPC section, i.e. assume there is one EPC section or
5506 * that all EPC sections have the same security properties.
5508 if (count > 1) {
5509 uint64_t epc_addr, epc_size;
5511 if (sgx_epc_get_section(count - 2, &epc_addr, &epc_size)) {
5512 *eax = *ebx = *ecx = *edx = 0;
5513 break;
5515 host_cpuid(index, 2, eax, ebx, ecx, edx);
5516 *eax = (uint32_t)(epc_addr & 0xfffff000) | 0x1;
5517 *ebx = (uint32_t)(epc_addr >> 32);
5518 *ecx = (uint32_t)(epc_size & 0xfffff000) | (*ecx & 0xf);
5519 *edx = (uint32_t)(epc_size >> 32);
5520 break;
5524 * SGX sub-leafs CPUID.0x12.{0x0,0x1} are heavily dependent on hardware
5525 * and KVM, i.e. QEMU cannot emulate features to override what KVM
5526 * supports. Features can be further restricted by userspace, but not
5527 * made more permissive.
5529 *eax = kvm_arch_get_supported_cpuid(cs->kvm_state, 0x12, count, R_EAX);
5530 *ebx = kvm_arch_get_supported_cpuid(cs->kvm_state, 0x12, count, R_EBX);
5531 *ecx = kvm_arch_get_supported_cpuid(cs->kvm_state, 0x12, count, R_ECX);
5532 *edx = kvm_arch_get_supported_cpuid(cs->kvm_state, 0x12, count, R_EDX);
5534 if (count == 0) {
5535 *eax &= env->features[FEAT_SGX_12_0_EAX];
5536 *ebx &= env->features[FEAT_SGX_12_0_EBX];
5537 } else {
5538 *eax &= env->features[FEAT_SGX_12_1_EAX];
5539 *ebx &= 0; /* ebx reserve */
5540 *ecx &= env->features[FEAT_XSAVE_COMP_LO];
5541 *edx &= env->features[FEAT_XSAVE_COMP_HI];
5543 /* FP and SSE are always allowed regardless of XSAVE/XCR0. */
5544 *ecx |= XSTATE_FP_MASK | XSTATE_SSE_MASK;
5546 /* Access to PROVISIONKEY requires additional credentials. */
5547 if ((*eax & (1U << 4)) &&
5548 !kvm_enable_sgx_provisioning(cs->kvm_state)) {
5549 *eax &= ~(1U << 4);
5552 #endif
5553 break;
5554 case 0x14: {
5555 /* Intel Processor Trace Enumeration */
5556 *eax = 0;
5557 *ebx = 0;
5558 *ecx = 0;
5559 *edx = 0;
5560 if (!(env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_INTEL_PT) ||
5561 !kvm_enabled()) {
5562 break;
5565 if (count == 0) {
5566 *eax = INTEL_PT_MAX_SUBLEAF;
5567 *ebx = INTEL_PT_MINIMAL_EBX;
5568 *ecx = INTEL_PT_MINIMAL_ECX;
5569 if (env->features[FEAT_14_0_ECX] & CPUID_14_0_ECX_LIP) {
5570 *ecx |= CPUID_14_0_ECX_LIP;
5572 } else if (count == 1) {
5573 *eax = INTEL_PT_MTC_BITMAP | INTEL_PT_ADDR_RANGES_NUM;
5574 *ebx = INTEL_PT_PSB_BITMAP | INTEL_PT_CYCLE_BITMAP;
5576 break;
5578 case 0x40000000:
5580 * CPUID code in kvm_arch_init_vcpu() ignores stuff
5581 * set here, but we restrict to TCG none the less.
5583 if (tcg_enabled() && cpu->expose_tcg) {
5584 memcpy(signature, "TCGTCGTCGTCG", 12);
5585 *eax = 0x40000001;
5586 *ebx = signature[0];
5587 *ecx = signature[1];
5588 *edx = signature[2];
5589 } else {
5590 *eax = 0;
5591 *ebx = 0;
5592 *ecx = 0;
5593 *edx = 0;
5595 break;
5596 case 0x40000001:
5597 *eax = 0;
5598 *ebx = 0;
5599 *ecx = 0;
5600 *edx = 0;
5601 break;
5602 case 0x80000000:
5603 *eax = env->cpuid_xlevel;
5604 *ebx = env->cpuid_vendor1;
5605 *edx = env->cpuid_vendor2;
5606 *ecx = env->cpuid_vendor3;
5607 break;
5608 case 0x80000001:
5609 *eax = env->cpuid_version;
5610 *ebx = 0;
5611 *ecx = env->features[FEAT_8000_0001_ECX];
5612 *edx = env->features[FEAT_8000_0001_EDX];
5614 /* The Linux kernel checks for the CMPLegacy bit and
5615 * discards multiple thread information if it is set.
5616 * So don't set it here for Intel to make Linux guests happy.
5618 if (cs->nr_cores * cs->nr_threads > 1) {
5619 if (env->cpuid_vendor1 != CPUID_VENDOR_INTEL_1 ||
5620 env->cpuid_vendor2 != CPUID_VENDOR_INTEL_2 ||
5621 env->cpuid_vendor3 != CPUID_VENDOR_INTEL_3) {
5622 *ecx |= 1 << 1; /* CmpLegacy bit */
5625 break;
5626 case 0x80000002:
5627 case 0x80000003:
5628 case 0x80000004:
5629 *eax = env->cpuid_model[(index - 0x80000002) * 4 + 0];
5630 *ebx = env->cpuid_model[(index - 0x80000002) * 4 + 1];
5631 *ecx = env->cpuid_model[(index - 0x80000002) * 4 + 2];
5632 *edx = env->cpuid_model[(index - 0x80000002) * 4 + 3];
5633 break;
5634 case 0x80000005:
5635 /* cache info (L1 cache) */
5636 if (cpu->cache_info_passthrough) {
5637 host_cpuid(index, 0, eax, ebx, ecx, edx);
5638 break;
5640 *eax = (L1_DTLB_2M_ASSOC << 24) | (L1_DTLB_2M_ENTRIES << 16) |
5641 (L1_ITLB_2M_ASSOC << 8) | (L1_ITLB_2M_ENTRIES);
5642 *ebx = (L1_DTLB_4K_ASSOC << 24) | (L1_DTLB_4K_ENTRIES << 16) |
5643 (L1_ITLB_4K_ASSOC << 8) | (L1_ITLB_4K_ENTRIES);
5644 *ecx = encode_cache_cpuid80000005(env->cache_info_amd.l1d_cache);
5645 *edx = encode_cache_cpuid80000005(env->cache_info_amd.l1i_cache);
5646 break;
5647 case 0x80000006:
5648 /* cache info (L2 cache) */
5649 if (cpu->cache_info_passthrough) {
5650 host_cpuid(index, 0, eax, ebx, ecx, edx);
5651 break;
5653 *eax = (AMD_ENC_ASSOC(L2_DTLB_2M_ASSOC) << 28) |
5654 (L2_DTLB_2M_ENTRIES << 16) |
5655 (AMD_ENC_ASSOC(L2_ITLB_2M_ASSOC) << 12) |
5656 (L2_ITLB_2M_ENTRIES);
5657 *ebx = (AMD_ENC_ASSOC(L2_DTLB_4K_ASSOC) << 28) |
5658 (L2_DTLB_4K_ENTRIES << 16) |
5659 (AMD_ENC_ASSOC(L2_ITLB_4K_ASSOC) << 12) |
5660 (L2_ITLB_4K_ENTRIES);
5661 encode_cache_cpuid80000006(env->cache_info_amd.l2_cache,
5662 cpu->enable_l3_cache ?
5663 env->cache_info_amd.l3_cache : NULL,
5664 ecx, edx);
5665 break;
5666 case 0x80000007:
5667 *eax = 0;
5668 *ebx = 0;
5669 *ecx = 0;
5670 *edx = env->features[FEAT_8000_0007_EDX];
5671 break;
5672 case 0x80000008:
5673 /* virtual & phys address size in low 2 bytes. */
5674 *eax = cpu->phys_bits;
5675 if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_LM) {
5676 /* 64 bit processor */
5677 *eax |= (cpu_x86_virtual_addr_width(env) << 8);
5679 *ebx = env->features[FEAT_8000_0008_EBX];
5680 if (cs->nr_cores * cs->nr_threads > 1) {
5682 * Bits 15:12 is "The number of bits in the initial
5683 * Core::X86::Apic::ApicId[ApicId] value that indicate
5684 * thread ID within a package".
5685 * Bits 7:0 is "The number of threads in the package is NC+1"
5687 *ecx = (apicid_pkg_offset(&topo_info) << 12) |
5688 ((cs->nr_cores * cs->nr_threads) - 1);
5689 } else {
5690 *ecx = 0;
5692 *edx = 0;
5693 break;
5694 case 0x8000000A:
5695 if (env->features[FEAT_8000_0001_ECX] & CPUID_EXT3_SVM) {
5696 *eax = 0x00000001; /* SVM Revision */
5697 *ebx = 0x00000010; /* nr of ASIDs */
5698 *ecx = 0;
5699 *edx = env->features[FEAT_SVM]; /* optional features */
5700 } else {
5701 *eax = 0;
5702 *ebx = 0;
5703 *ecx = 0;
5704 *edx = 0;
5706 break;
5707 case 0x8000001D:
5708 *eax = 0;
5709 if (cpu->cache_info_passthrough) {
5710 host_cpuid(index, count, eax, ebx, ecx, edx);
5711 break;
5713 switch (count) {
5714 case 0: /* L1 dcache info */
5715 encode_cache_cpuid8000001d(env->cache_info_amd.l1d_cache,
5716 &topo_info, eax, ebx, ecx, edx);
5717 break;
5718 case 1: /* L1 icache info */
5719 encode_cache_cpuid8000001d(env->cache_info_amd.l1i_cache,
5720 &topo_info, eax, ebx, ecx, edx);
5721 break;
5722 case 2: /* L2 cache info */
5723 encode_cache_cpuid8000001d(env->cache_info_amd.l2_cache,
5724 &topo_info, eax, ebx, ecx, edx);
5725 break;
5726 case 3: /* L3 cache info */
5727 encode_cache_cpuid8000001d(env->cache_info_amd.l3_cache,
5728 &topo_info, eax, ebx, ecx, edx);
5729 break;
5730 default: /* end of info */
5731 *eax = *ebx = *ecx = *edx = 0;
5732 break;
5734 break;
5735 case 0x8000001E:
5736 if (cpu->core_id <= 255) {
5737 encode_topo_cpuid8000001e(cpu, &topo_info, eax, ebx, ecx, edx);
5738 } else {
5739 *eax = 0;
5740 *ebx = 0;
5741 *ecx = 0;
5742 *edx = 0;
5744 break;
5745 case 0xC0000000:
5746 *eax = env->cpuid_xlevel2;
5747 *ebx = 0;
5748 *ecx = 0;
5749 *edx = 0;
5750 break;
5751 case 0xC0000001:
5752 /* Support for VIA CPU's CPUID instruction */
5753 *eax = env->cpuid_version;
5754 *ebx = 0;
5755 *ecx = 0;
5756 *edx = env->features[FEAT_C000_0001_EDX];
5757 break;
5758 case 0xC0000002:
5759 case 0xC0000003:
5760 case 0xC0000004:
5761 /* Reserved for the future, and now filled with zero */
5762 *eax = 0;
5763 *ebx = 0;
5764 *ecx = 0;
5765 *edx = 0;
5766 break;
5767 case 0x8000001F:
5768 *eax = *ebx = *ecx = *edx = 0;
5769 if (sev_enabled()) {
5770 *eax = 0x2;
5771 *eax |= sev_es_enabled() ? 0x8 : 0;
5772 *ebx = sev_get_cbit_position();
5773 *ebx |= sev_get_reduced_phys_bits() << 6;
5775 break;
5776 default:
5777 /* reserved values: zero */
5778 *eax = 0;
5779 *ebx = 0;
5780 *ecx = 0;
5781 *edx = 0;
5782 break;
5786 static void x86_cpu_set_sgxlepubkeyhash(CPUX86State *env)
5788 #ifndef CONFIG_USER_ONLY
5789 /* Those default values are defined in Skylake HW */
5790 env->msr_ia32_sgxlepubkeyhash[0] = 0xa6053e051270b7acULL;
5791 env->msr_ia32_sgxlepubkeyhash[1] = 0x6cfbe8ba8b3b413dULL;
5792 env->msr_ia32_sgxlepubkeyhash[2] = 0xc4916d99f2b3735dULL;
5793 env->msr_ia32_sgxlepubkeyhash[3] = 0xd4f8c05909f9bb3bULL;
5794 #endif
5797 static void x86_cpu_reset(DeviceState *dev)
5799 CPUState *s = CPU(dev);
5800 X86CPU *cpu = X86_CPU(s);
5801 X86CPUClass *xcc = X86_CPU_GET_CLASS(cpu);
5802 CPUX86State *env = &cpu->env;
5803 target_ulong cr4;
5804 uint64_t xcr0;
5805 int i;
5807 xcc->parent_reset(dev);
5809 memset(env, 0, offsetof(CPUX86State, end_reset_fields));
5811 env->old_exception = -1;
5813 /* init to reset state */
5814 env->int_ctl = 0;
5815 env->hflags2 |= HF2_GIF_MASK;
5816 env->hflags2 |= HF2_VGIF_MASK;
5817 env->hflags &= ~HF_GUEST_MASK;
5819 cpu_x86_update_cr0(env, 0x60000010);
5820 env->a20_mask = ~0x0;
5821 env->smbase = 0x30000;
5822 env->msr_smi_count = 0;
5824 env->idt.limit = 0xffff;
5825 env->gdt.limit = 0xffff;
5826 env->ldt.limit = 0xffff;
5827 env->ldt.flags = DESC_P_MASK | (2 << DESC_TYPE_SHIFT);
5828 env->tr.limit = 0xffff;
5829 env->tr.flags = DESC_P_MASK | (11 << DESC_TYPE_SHIFT);
5831 cpu_x86_load_seg_cache(env, R_CS, 0xf000, 0xffff0000, 0xffff,
5832 DESC_P_MASK | DESC_S_MASK | DESC_CS_MASK |
5833 DESC_R_MASK | DESC_A_MASK);
5834 cpu_x86_load_seg_cache(env, R_DS, 0, 0, 0xffff,
5835 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
5836 DESC_A_MASK);
5837 cpu_x86_load_seg_cache(env, R_ES, 0, 0, 0xffff,
5838 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
5839 DESC_A_MASK);
5840 cpu_x86_load_seg_cache(env, R_SS, 0, 0, 0xffff,
5841 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
5842 DESC_A_MASK);
5843 cpu_x86_load_seg_cache(env, R_FS, 0, 0, 0xffff,
5844 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
5845 DESC_A_MASK);
5846 cpu_x86_load_seg_cache(env, R_GS, 0, 0, 0xffff,
5847 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
5848 DESC_A_MASK);
5850 env->eip = 0xfff0;
5851 env->regs[R_EDX] = env->cpuid_version;
5853 env->eflags = 0x2;
5855 /* FPU init */
5856 for (i = 0; i < 8; i++) {
5857 env->fptags[i] = 1;
5859 cpu_set_fpuc(env, 0x37f);
5861 env->mxcsr = 0x1f80;
5862 /* All units are in INIT state. */
5863 env->xstate_bv = 0;
5865 env->pat = 0x0007040600070406ULL;
5866 env->msr_ia32_misc_enable = MSR_IA32_MISC_ENABLE_DEFAULT;
5867 if (env->features[FEAT_1_ECX] & CPUID_EXT_MONITOR) {
5868 env->msr_ia32_misc_enable |= MSR_IA32_MISC_ENABLE_MWAIT;
5871 memset(env->dr, 0, sizeof(env->dr));
5872 env->dr[6] = DR6_FIXED_1;
5873 env->dr[7] = DR7_FIXED_1;
5874 cpu_breakpoint_remove_all(s, BP_CPU);
5875 cpu_watchpoint_remove_all(s, BP_CPU);
5877 cr4 = 0;
5878 xcr0 = XSTATE_FP_MASK;
5880 #ifdef CONFIG_USER_ONLY
5881 /* Enable all the features for user-mode. */
5882 if (env->features[FEAT_1_EDX] & CPUID_SSE) {
5883 xcr0 |= XSTATE_SSE_MASK;
5885 for (i = 2; i < ARRAY_SIZE(x86_ext_save_areas); i++) {
5886 const ExtSaveArea *esa = &x86_ext_save_areas[i];
5887 if (env->features[esa->feature] & esa->bits) {
5888 xcr0 |= 1ull << i;
5892 if (env->features[FEAT_1_ECX] & CPUID_EXT_XSAVE) {
5893 cr4 |= CR4_OSFXSR_MASK | CR4_OSXSAVE_MASK;
5895 if (env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_FSGSBASE) {
5896 cr4 |= CR4_FSGSBASE_MASK;
5898 #endif
5900 env->xcr0 = xcr0;
5901 cpu_x86_update_cr4(env, cr4);
5904 * SDM 11.11.5 requires:
5905 * - IA32_MTRR_DEF_TYPE MSR.E = 0
5906 * - IA32_MTRR_PHYSMASKn.V = 0
5907 * All other bits are undefined. For simplification, zero it all.
5909 env->mtrr_deftype = 0;
5910 memset(env->mtrr_var, 0, sizeof(env->mtrr_var));
5911 memset(env->mtrr_fixed, 0, sizeof(env->mtrr_fixed));
5913 env->interrupt_injected = -1;
5914 env->exception_nr = -1;
5915 env->exception_pending = 0;
5916 env->exception_injected = 0;
5917 env->exception_has_payload = false;
5918 env->exception_payload = 0;
5919 env->nmi_injected = false;
5920 #if !defined(CONFIG_USER_ONLY)
5921 /* We hard-wire the BSP to the first CPU. */
5922 apic_designate_bsp(cpu->apic_state, s->cpu_index == 0);
5924 s->halted = !cpu_is_bsp(cpu);
5926 if (kvm_enabled()) {
5927 kvm_arch_reset_vcpu(cpu);
5930 x86_cpu_set_sgxlepubkeyhash(env);
5932 if (env->features[FEAT_SVM] & CPUID_SVM_TSCSCALE) {
5933 env->amd_tsc_scale_msr = MSR_AMD64_TSC_RATIO_DEFAULT;
5936 #endif
5939 static void mce_init(X86CPU *cpu)
5941 CPUX86State *cenv = &cpu->env;
5942 unsigned int bank;
5944 if (((cenv->cpuid_version >> 8) & 0xf) >= 6
5945 && (cenv->features[FEAT_1_EDX] & (CPUID_MCE | CPUID_MCA)) ==
5946 (CPUID_MCE | CPUID_MCA)) {
5947 cenv->mcg_cap = MCE_CAP_DEF | MCE_BANKS_DEF |
5948 (cpu->enable_lmce ? MCG_LMCE_P : 0);
5949 cenv->mcg_ctl = ~(uint64_t)0;
5950 for (bank = 0; bank < MCE_BANKS_DEF; bank++) {
5951 cenv->mce_banks[bank * 4] = ~(uint64_t)0;
5956 static void x86_cpu_adjust_level(X86CPU *cpu, uint32_t *min, uint32_t value)
5958 if (*min < value) {
5959 *min = value;
5963 /* Increase cpuid_min_{level,xlevel,xlevel2} automatically, if appropriate */
5964 static void x86_cpu_adjust_feat_level(X86CPU *cpu, FeatureWord w)
5966 CPUX86State *env = &cpu->env;
5967 FeatureWordInfo *fi = &feature_word_info[w];
5968 uint32_t eax = fi->cpuid.eax;
5969 uint32_t region = eax & 0xF0000000;
5971 assert(feature_word_info[w].type == CPUID_FEATURE_WORD);
5972 if (!env->features[w]) {
5973 return;
5976 switch (region) {
5977 case 0x00000000:
5978 x86_cpu_adjust_level(cpu, &env->cpuid_min_level, eax);
5979 break;
5980 case 0x80000000:
5981 x86_cpu_adjust_level(cpu, &env->cpuid_min_xlevel, eax);
5982 break;
5983 case 0xC0000000:
5984 x86_cpu_adjust_level(cpu, &env->cpuid_min_xlevel2, eax);
5985 break;
5988 if (eax == 7) {
5989 x86_cpu_adjust_level(cpu, &env->cpuid_min_level_func7,
5990 fi->cpuid.ecx);
5994 /* Calculate XSAVE components based on the configured CPU feature flags */
5995 static void x86_cpu_enable_xsave_components(X86CPU *cpu)
5997 CPUX86State *env = &cpu->env;
5998 int i;
5999 uint64_t mask;
6001 if (!(env->features[FEAT_1_ECX] & CPUID_EXT_XSAVE)) {
6002 env->features[FEAT_XSAVE_COMP_LO] = 0;
6003 env->features[FEAT_XSAVE_COMP_HI] = 0;
6004 return;
6007 mask = 0;
6008 for (i = 0; i < ARRAY_SIZE(x86_ext_save_areas); i++) {
6009 const ExtSaveArea *esa = &x86_ext_save_areas[i];
6010 if (env->features[esa->feature] & esa->bits) {
6011 mask |= (1ULL << i);
6015 env->features[FEAT_XSAVE_COMP_LO] = mask;
6016 env->features[FEAT_XSAVE_COMP_HI] = mask >> 32;
6019 /***** Steps involved on loading and filtering CPUID data
6021 * When initializing and realizing a CPU object, the steps
6022 * involved in setting up CPUID data are:
6024 * 1) Loading CPU model definition (X86CPUDefinition). This is
6025 * implemented by x86_cpu_load_model() and should be completely
6026 * transparent, as it is done automatically by instance_init.
6027 * No code should need to look at X86CPUDefinition structs
6028 * outside instance_init.
6030 * 2) CPU expansion. This is done by realize before CPUID
6031 * filtering, and will make sure host/accelerator data is
6032 * loaded for CPU models that depend on host capabilities
6033 * (e.g. "host"). Done by x86_cpu_expand_features().
6035 * 3) CPUID filtering. This initializes extra data related to
6036 * CPUID, and checks if the host supports all capabilities
6037 * required by the CPU. Runnability of a CPU model is
6038 * determined at this step. Done by x86_cpu_filter_features().
6040 * Some operations don't require all steps to be performed.
6041 * More precisely:
6043 * - CPU instance creation (instance_init) will run only CPU
6044 * model loading. CPU expansion can't run at instance_init-time
6045 * because host/accelerator data may be not available yet.
6046 * - CPU realization will perform both CPU model expansion and CPUID
6047 * filtering, and return an error in case one of them fails.
6048 * - query-cpu-definitions needs to run all 3 steps. It needs
6049 * to run CPUID filtering, as the 'unavailable-features'
6050 * field is set based on the filtering results.
6051 * - The query-cpu-model-expansion QMP command only needs to run
6052 * CPU model loading and CPU expansion. It should not filter
6053 * any CPUID data based on host capabilities.
6056 /* Expand CPU configuration data, based on configured features
6057 * and host/accelerator capabilities when appropriate.
6059 void x86_cpu_expand_features(X86CPU *cpu, Error **errp)
6061 CPUX86State *env = &cpu->env;
6062 FeatureWord w;
6063 int i;
6064 GList *l;
6066 for (l = plus_features; l; l = l->next) {
6067 const char *prop = l->data;
6068 if (!object_property_set_bool(OBJECT(cpu), prop, true, errp)) {
6069 return;
6073 for (l = minus_features; l; l = l->next) {
6074 const char *prop = l->data;
6075 if (!object_property_set_bool(OBJECT(cpu), prop, false, errp)) {
6076 return;
6080 /*TODO: Now cpu->max_features doesn't overwrite features
6081 * set using QOM properties, and we can convert
6082 * plus_features & minus_features to global properties
6083 * inside x86_cpu_parse_featurestr() too.
6085 if (cpu->max_features) {
6086 for (w = 0; w < FEATURE_WORDS; w++) {
6087 /* Override only features that weren't set explicitly
6088 * by the user.
6090 env->features[w] |=
6091 x86_cpu_get_supported_feature_word(w, cpu->migratable) &
6092 ~env->user_features[w] &
6093 ~feature_word_info[w].no_autoenable_flags;
6097 for (i = 0; i < ARRAY_SIZE(feature_dependencies); i++) {
6098 FeatureDep *d = &feature_dependencies[i];
6099 if (!(env->features[d->from.index] & d->from.mask)) {
6100 uint64_t unavailable_features = env->features[d->to.index] & d->to.mask;
6102 /* Not an error unless the dependent feature was added explicitly. */
6103 mark_unavailable_features(cpu, d->to.index,
6104 unavailable_features & env->user_features[d->to.index],
6105 "This feature depends on other features that were not requested");
6107 env->features[d->to.index] &= ~unavailable_features;
6111 if (!kvm_enabled() || !cpu->expose_kvm) {
6112 env->features[FEAT_KVM] = 0;
6115 x86_cpu_enable_xsave_components(cpu);
6117 /* CPUID[EAX=7,ECX=0].EBX always increased level automatically: */
6118 x86_cpu_adjust_feat_level(cpu, FEAT_7_0_EBX);
6119 if (cpu->full_cpuid_auto_level) {
6120 x86_cpu_adjust_feat_level(cpu, FEAT_1_EDX);
6121 x86_cpu_adjust_feat_level(cpu, FEAT_1_ECX);
6122 x86_cpu_adjust_feat_level(cpu, FEAT_6_EAX);
6123 x86_cpu_adjust_feat_level(cpu, FEAT_7_0_ECX);
6124 x86_cpu_adjust_feat_level(cpu, FEAT_7_1_EAX);
6125 x86_cpu_adjust_feat_level(cpu, FEAT_8000_0001_EDX);
6126 x86_cpu_adjust_feat_level(cpu, FEAT_8000_0001_ECX);
6127 x86_cpu_adjust_feat_level(cpu, FEAT_8000_0007_EDX);
6128 x86_cpu_adjust_feat_level(cpu, FEAT_8000_0008_EBX);
6129 x86_cpu_adjust_feat_level(cpu, FEAT_C000_0001_EDX);
6130 x86_cpu_adjust_feat_level(cpu, FEAT_SVM);
6131 x86_cpu_adjust_feat_level(cpu, FEAT_XSAVE);
6133 /* Intel Processor Trace requires CPUID[0x14] */
6134 if ((env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_INTEL_PT)) {
6135 if (cpu->intel_pt_auto_level) {
6136 x86_cpu_adjust_level(cpu, &cpu->env.cpuid_min_level, 0x14);
6137 } else if (cpu->env.cpuid_min_level < 0x14) {
6138 mark_unavailable_features(cpu, FEAT_7_0_EBX,
6139 CPUID_7_0_EBX_INTEL_PT,
6140 "Intel PT need CPUID leaf 0x14, please set by \"-cpu ...,intel-pt=on,min-level=0x14\"");
6145 * Intel CPU topology with multi-dies support requires CPUID[0x1F].
6146 * For AMD Rome/Milan, cpuid level is 0x10, and guest OS should detect
6147 * extended toplogy by leaf 0xB. Only adjust it for Intel CPU, unless
6148 * cpu->vendor_cpuid_only has been unset for compatibility with older
6149 * machine types.
6151 if ((env->nr_dies > 1) &&
6152 (IS_INTEL_CPU(env) || !cpu->vendor_cpuid_only)) {
6153 x86_cpu_adjust_level(cpu, &env->cpuid_min_level, 0x1F);
6156 /* SVM requires CPUID[0x8000000A] */
6157 if (env->features[FEAT_8000_0001_ECX] & CPUID_EXT3_SVM) {
6158 x86_cpu_adjust_level(cpu, &env->cpuid_min_xlevel, 0x8000000A);
6161 /* SEV requires CPUID[0x8000001F] */
6162 if (sev_enabled()) {
6163 x86_cpu_adjust_level(cpu, &env->cpuid_min_xlevel, 0x8000001F);
6166 /* SGX requires CPUID[0x12] for EPC enumeration */
6167 if (env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_SGX) {
6168 x86_cpu_adjust_level(cpu, &env->cpuid_min_level, 0x12);
6172 /* Set cpuid_*level* based on cpuid_min_*level, if not explicitly set */
6173 if (env->cpuid_level_func7 == UINT32_MAX) {
6174 env->cpuid_level_func7 = env->cpuid_min_level_func7;
6176 if (env->cpuid_level == UINT32_MAX) {
6177 env->cpuid_level = env->cpuid_min_level;
6179 if (env->cpuid_xlevel == UINT32_MAX) {
6180 env->cpuid_xlevel = env->cpuid_min_xlevel;
6182 if (env->cpuid_xlevel2 == UINT32_MAX) {
6183 env->cpuid_xlevel2 = env->cpuid_min_xlevel2;
6186 if (kvm_enabled()) {
6187 kvm_hyperv_expand_features(cpu, errp);
6192 * Finishes initialization of CPUID data, filters CPU feature
6193 * words based on host availability of each feature.
6195 * Returns: 0 if all flags are supported by the host, non-zero otherwise.
6197 static void x86_cpu_filter_features(X86CPU *cpu, bool verbose)
6199 CPUX86State *env = &cpu->env;
6200 FeatureWord w;
6201 const char *prefix = NULL;
6203 if (verbose) {
6204 prefix = accel_uses_host_cpuid()
6205 ? "host doesn't support requested feature"
6206 : "TCG doesn't support requested feature";
6209 for (w = 0; w < FEATURE_WORDS; w++) {
6210 uint64_t host_feat =
6211 x86_cpu_get_supported_feature_word(w, false);
6212 uint64_t requested_features = env->features[w];
6213 uint64_t unavailable_features = requested_features & ~host_feat;
6214 mark_unavailable_features(cpu, w, unavailable_features, prefix);
6217 if ((env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_INTEL_PT) &&
6218 kvm_enabled()) {
6219 KVMState *s = CPU(cpu)->kvm_state;
6220 uint32_t eax_0 = kvm_arch_get_supported_cpuid(s, 0x14, 0, R_EAX);
6221 uint32_t ebx_0 = kvm_arch_get_supported_cpuid(s, 0x14, 0, R_EBX);
6222 uint32_t ecx_0 = kvm_arch_get_supported_cpuid(s, 0x14, 0, R_ECX);
6223 uint32_t eax_1 = kvm_arch_get_supported_cpuid(s, 0x14, 1, R_EAX);
6224 uint32_t ebx_1 = kvm_arch_get_supported_cpuid(s, 0x14, 1, R_EBX);
6226 if (!eax_0 ||
6227 ((ebx_0 & INTEL_PT_MINIMAL_EBX) != INTEL_PT_MINIMAL_EBX) ||
6228 ((ecx_0 & INTEL_PT_MINIMAL_ECX) != INTEL_PT_MINIMAL_ECX) ||
6229 ((eax_1 & INTEL_PT_MTC_BITMAP) != INTEL_PT_MTC_BITMAP) ||
6230 ((eax_1 & INTEL_PT_ADDR_RANGES_NUM_MASK) <
6231 INTEL_PT_ADDR_RANGES_NUM) ||
6232 ((ebx_1 & (INTEL_PT_PSB_BITMAP | INTEL_PT_CYCLE_BITMAP)) !=
6233 (INTEL_PT_PSB_BITMAP | INTEL_PT_CYCLE_BITMAP)) ||
6234 ((ecx_0 & CPUID_14_0_ECX_LIP) !=
6235 (env->features[FEAT_14_0_ECX] & CPUID_14_0_ECX_LIP))) {
6237 * Processor Trace capabilities aren't configurable, so if the
6238 * host can't emulate the capabilities we report on
6239 * cpu_x86_cpuid(), intel-pt can't be enabled on the current host.
6241 mark_unavailable_features(cpu, FEAT_7_0_EBX, CPUID_7_0_EBX_INTEL_PT, prefix);
6246 static void x86_cpu_hyperv_realize(X86CPU *cpu)
6248 size_t len;
6250 /* Hyper-V vendor id */
6251 if (!cpu->hyperv_vendor) {
6252 object_property_set_str(OBJECT(cpu), "hv-vendor-id", "Microsoft Hv",
6253 &error_abort);
6255 len = strlen(cpu->hyperv_vendor);
6256 if (len > 12) {
6257 warn_report("hv-vendor-id truncated to 12 characters");
6258 len = 12;
6260 memset(cpu->hyperv_vendor_id, 0, 12);
6261 memcpy(cpu->hyperv_vendor_id, cpu->hyperv_vendor, len);
6263 /* 'Hv#1' interface identification*/
6264 cpu->hyperv_interface_id[0] = 0x31237648;
6265 cpu->hyperv_interface_id[1] = 0;
6266 cpu->hyperv_interface_id[2] = 0;
6267 cpu->hyperv_interface_id[3] = 0;
6269 /* Hypervisor implementation limits */
6270 cpu->hyperv_limits[0] = 64;
6271 cpu->hyperv_limits[1] = 0;
6272 cpu->hyperv_limits[2] = 0;
6275 static void x86_cpu_realizefn(DeviceState *dev, Error **errp)
6277 CPUState *cs = CPU(dev);
6278 X86CPU *cpu = X86_CPU(dev);
6279 X86CPUClass *xcc = X86_CPU_GET_CLASS(dev);
6280 CPUX86State *env = &cpu->env;
6281 Error *local_err = NULL;
6282 static bool ht_warned;
6284 if (cpu->apic_id == UNASSIGNED_APIC_ID) {
6285 error_setg(errp, "apic-id property was not initialized properly");
6286 return;
6290 * Process Hyper-V enlightenments.
6291 * Note: this currently has to happen before the expansion of CPU features.
6293 x86_cpu_hyperv_realize(cpu);
6295 x86_cpu_expand_features(cpu, &local_err);
6296 if (local_err) {
6297 goto out;
6300 x86_cpu_filter_features(cpu, cpu->check_cpuid || cpu->enforce_cpuid);
6302 if (cpu->enforce_cpuid && x86_cpu_have_filtered_features(cpu)) {
6303 error_setg(&local_err,
6304 accel_uses_host_cpuid() ?
6305 "Host doesn't support requested features" :
6306 "TCG doesn't support requested features");
6307 goto out;
6310 /* On AMD CPUs, some CPUID[8000_0001].EDX bits must match the bits on
6311 * CPUID[1].EDX.
6313 if (IS_AMD_CPU(env)) {
6314 env->features[FEAT_8000_0001_EDX] &= ~CPUID_EXT2_AMD_ALIASES;
6315 env->features[FEAT_8000_0001_EDX] |= (env->features[FEAT_1_EDX]
6316 & CPUID_EXT2_AMD_ALIASES);
6319 x86_cpu_set_sgxlepubkeyhash(env);
6322 * note: the call to the framework needs to happen after feature expansion,
6323 * but before the checks/modifications to ucode_rev, mwait, phys_bits.
6324 * These may be set by the accel-specific code,
6325 * and the results are subsequently checked / assumed in this function.
6327 cpu_exec_realizefn(cs, &local_err);
6328 if (local_err != NULL) {
6329 error_propagate(errp, local_err);
6330 return;
6333 if (xcc->host_cpuid_required && !accel_uses_host_cpuid()) {
6334 g_autofree char *name = x86_cpu_class_get_model_name(xcc);
6335 error_setg(&local_err, "CPU model '%s' requires KVM or HVF", name);
6336 goto out;
6339 if (cpu->ucode_rev == 0) {
6341 * The default is the same as KVM's. Note that this check
6342 * needs to happen after the evenual setting of ucode_rev in
6343 * accel-specific code in cpu_exec_realizefn.
6345 if (IS_AMD_CPU(env)) {
6346 cpu->ucode_rev = 0x01000065;
6347 } else {
6348 cpu->ucode_rev = 0x100000000ULL;
6353 * mwait extended info: needed for Core compatibility
6354 * We always wake on interrupt even if host does not have the capability.
6356 * requires the accel-specific code in cpu_exec_realizefn to
6357 * have already acquired the CPUID data into cpu->mwait.
6359 cpu->mwait.ecx |= CPUID_MWAIT_EMX | CPUID_MWAIT_IBE;
6361 /* For 64bit systems think about the number of physical bits to present.
6362 * ideally this should be the same as the host; anything other than matching
6363 * the host can cause incorrect guest behaviour.
6364 * QEMU used to pick the magic value of 40 bits that corresponds to
6365 * consumer AMD devices but nothing else.
6367 * Note that this code assumes features expansion has already been done
6368 * (as it checks for CPUID_EXT2_LM), and also assumes that potential
6369 * phys_bits adjustments to match the host have been already done in
6370 * accel-specific code in cpu_exec_realizefn.
6372 if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_LM) {
6373 if (cpu->phys_bits &&
6374 (cpu->phys_bits > TARGET_PHYS_ADDR_SPACE_BITS ||
6375 cpu->phys_bits < 32)) {
6376 error_setg(errp, "phys-bits should be between 32 and %u "
6377 " (but is %u)",
6378 TARGET_PHYS_ADDR_SPACE_BITS, cpu->phys_bits);
6379 return;
6382 * 0 means it was not explicitly set by the user (or by machine
6383 * compat_props or by the host code in host-cpu.c).
6384 * In this case, the default is the value used by TCG (40).
6386 if (cpu->phys_bits == 0) {
6387 cpu->phys_bits = TCG_PHYS_ADDR_BITS;
6389 } else {
6390 /* For 32 bit systems don't use the user set value, but keep
6391 * phys_bits consistent with what we tell the guest.
6393 if (cpu->phys_bits != 0) {
6394 error_setg(errp, "phys-bits is not user-configurable in 32 bit");
6395 return;
6398 if (env->features[FEAT_1_EDX] & CPUID_PSE36) {
6399 cpu->phys_bits = 36;
6400 } else {
6401 cpu->phys_bits = 32;
6405 /* Cache information initialization */
6406 if (!cpu->legacy_cache) {
6407 if (!xcc->model || !xcc->model->cpudef->cache_info) {
6408 g_autofree char *name = x86_cpu_class_get_model_name(xcc);
6409 error_setg(errp,
6410 "CPU model '%s' doesn't support legacy-cache=off", name);
6411 return;
6413 env->cache_info_cpuid2 = env->cache_info_cpuid4 = env->cache_info_amd =
6414 *xcc->model->cpudef->cache_info;
6415 } else {
6416 /* Build legacy cache information */
6417 env->cache_info_cpuid2.l1d_cache = &legacy_l1d_cache;
6418 env->cache_info_cpuid2.l1i_cache = &legacy_l1i_cache;
6419 env->cache_info_cpuid2.l2_cache = &legacy_l2_cache_cpuid2;
6420 env->cache_info_cpuid2.l3_cache = &legacy_l3_cache;
6422 env->cache_info_cpuid4.l1d_cache = &legacy_l1d_cache;
6423 env->cache_info_cpuid4.l1i_cache = &legacy_l1i_cache;
6424 env->cache_info_cpuid4.l2_cache = &legacy_l2_cache;
6425 env->cache_info_cpuid4.l3_cache = &legacy_l3_cache;
6427 env->cache_info_amd.l1d_cache = &legacy_l1d_cache_amd;
6428 env->cache_info_amd.l1i_cache = &legacy_l1i_cache_amd;
6429 env->cache_info_amd.l2_cache = &legacy_l2_cache_amd;
6430 env->cache_info_amd.l3_cache = &legacy_l3_cache;
6433 #ifndef CONFIG_USER_ONLY
6434 MachineState *ms = MACHINE(qdev_get_machine());
6435 qemu_register_reset(x86_cpu_machine_reset_cb, cpu);
6437 if (cpu->env.features[FEAT_1_EDX] & CPUID_APIC || ms->smp.cpus > 1) {
6438 x86_cpu_apic_create(cpu, &local_err);
6439 if (local_err != NULL) {
6440 goto out;
6443 #endif
6445 mce_init(cpu);
6447 qemu_init_vcpu(cs);
6450 * Most Intel and certain AMD CPUs support hyperthreading. Even though QEMU
6451 * fixes this issue by adjusting CPUID_0000_0001_EBX and CPUID_8000_0008_ECX
6452 * based on inputs (sockets,cores,threads), it is still better to give
6453 * users a warning.
6455 * NOTE: the following code has to follow qemu_init_vcpu(). Otherwise
6456 * cs->nr_threads hasn't be populated yet and the checking is incorrect.
6458 if (IS_AMD_CPU(env) &&
6459 !(env->features[FEAT_8000_0001_ECX] & CPUID_EXT3_TOPOEXT) &&
6460 cs->nr_threads > 1 && !ht_warned) {
6461 warn_report("This family of AMD CPU doesn't support "
6462 "hyperthreading(%d)",
6463 cs->nr_threads);
6464 error_printf("Please configure -smp options properly"
6465 " or try enabling topoext feature.\n");
6466 ht_warned = true;
6469 #ifndef CONFIG_USER_ONLY
6470 x86_cpu_apic_realize(cpu, &local_err);
6471 if (local_err != NULL) {
6472 goto out;
6474 #endif /* !CONFIG_USER_ONLY */
6475 cpu_reset(cs);
6477 xcc->parent_realize(dev, &local_err);
6479 out:
6480 if (local_err != NULL) {
6481 error_propagate(errp, local_err);
6482 return;
6486 static void x86_cpu_unrealizefn(DeviceState *dev)
6488 X86CPU *cpu = X86_CPU(dev);
6489 X86CPUClass *xcc = X86_CPU_GET_CLASS(dev);
6491 #ifndef CONFIG_USER_ONLY
6492 cpu_remove_sync(CPU(dev));
6493 qemu_unregister_reset(x86_cpu_machine_reset_cb, dev);
6494 #endif
6496 if (cpu->apic_state) {
6497 object_unparent(OBJECT(cpu->apic_state));
6498 cpu->apic_state = NULL;
6501 xcc->parent_unrealize(dev);
6504 typedef struct BitProperty {
6505 FeatureWord w;
6506 uint64_t mask;
6507 } BitProperty;
6509 static void x86_cpu_get_bit_prop(Object *obj, Visitor *v, const char *name,
6510 void *opaque, Error **errp)
6512 X86CPU *cpu = X86_CPU(obj);
6513 BitProperty *fp = opaque;
6514 uint64_t f = cpu->env.features[fp->w];
6515 bool value = (f & fp->mask) == fp->mask;
6516 visit_type_bool(v, name, &value, errp);
6519 static void x86_cpu_set_bit_prop(Object *obj, Visitor *v, const char *name,
6520 void *opaque, Error **errp)
6522 DeviceState *dev = DEVICE(obj);
6523 X86CPU *cpu = X86_CPU(obj);
6524 BitProperty *fp = opaque;
6525 bool value;
6527 if (dev->realized) {
6528 qdev_prop_set_after_realize(dev, name, errp);
6529 return;
6532 if (!visit_type_bool(v, name, &value, errp)) {
6533 return;
6536 if (value) {
6537 cpu->env.features[fp->w] |= fp->mask;
6538 } else {
6539 cpu->env.features[fp->w] &= ~fp->mask;
6541 cpu->env.user_features[fp->w] |= fp->mask;
6544 /* Register a boolean property to get/set a single bit in a uint32_t field.
6546 * The same property name can be registered multiple times to make it affect
6547 * multiple bits in the same FeatureWord. In that case, the getter will return
6548 * true only if all bits are set.
6550 static void x86_cpu_register_bit_prop(X86CPUClass *xcc,
6551 const char *prop_name,
6552 FeatureWord w,
6553 int bitnr)
6555 ObjectClass *oc = OBJECT_CLASS(xcc);
6556 BitProperty *fp;
6557 ObjectProperty *op;
6558 uint64_t mask = (1ULL << bitnr);
6560 op = object_class_property_find(oc, prop_name);
6561 if (op) {
6562 fp = op->opaque;
6563 assert(fp->w == w);
6564 fp->mask |= mask;
6565 } else {
6566 fp = g_new0(BitProperty, 1);
6567 fp->w = w;
6568 fp->mask = mask;
6569 object_class_property_add(oc, prop_name, "bool",
6570 x86_cpu_get_bit_prop,
6571 x86_cpu_set_bit_prop,
6572 NULL, fp);
6576 static void x86_cpu_register_feature_bit_props(X86CPUClass *xcc,
6577 FeatureWord w,
6578 int bitnr)
6580 FeatureWordInfo *fi = &feature_word_info[w];
6581 const char *name = fi->feat_names[bitnr];
6583 if (!name) {
6584 return;
6587 /* Property names should use "-" instead of "_".
6588 * Old names containing underscores are registered as aliases
6589 * using object_property_add_alias()
6591 assert(!strchr(name, '_'));
6592 /* aliases don't use "|" delimiters anymore, they are registered
6593 * manually using object_property_add_alias() */
6594 assert(!strchr(name, '|'));
6595 x86_cpu_register_bit_prop(xcc, name, w, bitnr);
6598 static void x86_cpu_post_initfn(Object *obj)
6600 accel_cpu_instance_init(CPU(obj));
6603 static void x86_cpu_initfn(Object *obj)
6605 X86CPU *cpu = X86_CPU(obj);
6606 X86CPUClass *xcc = X86_CPU_GET_CLASS(obj);
6607 CPUX86State *env = &cpu->env;
6609 env->nr_dies = 1;
6610 cpu_set_cpustate_pointers(cpu);
6612 object_property_add(obj, "feature-words", "X86CPUFeatureWordInfo",
6613 x86_cpu_get_feature_words,
6614 NULL, NULL, (void *)env->features);
6615 object_property_add(obj, "filtered-features", "X86CPUFeatureWordInfo",
6616 x86_cpu_get_feature_words,
6617 NULL, NULL, (void *)cpu->filtered_features);
6619 object_property_add_alias(obj, "sse3", obj, "pni");
6620 object_property_add_alias(obj, "pclmuldq", obj, "pclmulqdq");
6621 object_property_add_alias(obj, "sse4-1", obj, "sse4.1");
6622 object_property_add_alias(obj, "sse4-2", obj, "sse4.2");
6623 object_property_add_alias(obj, "xd", obj, "nx");
6624 object_property_add_alias(obj, "ffxsr", obj, "fxsr-opt");
6625 object_property_add_alias(obj, "i64", obj, "lm");
6627 object_property_add_alias(obj, "ds_cpl", obj, "ds-cpl");
6628 object_property_add_alias(obj, "tsc_adjust", obj, "tsc-adjust");
6629 object_property_add_alias(obj, "fxsr_opt", obj, "fxsr-opt");
6630 object_property_add_alias(obj, "lahf_lm", obj, "lahf-lm");
6631 object_property_add_alias(obj, "cmp_legacy", obj, "cmp-legacy");
6632 object_property_add_alias(obj, "nodeid_msr", obj, "nodeid-msr");
6633 object_property_add_alias(obj, "perfctr_core", obj, "perfctr-core");
6634 object_property_add_alias(obj, "perfctr_nb", obj, "perfctr-nb");
6635 object_property_add_alias(obj, "kvm_nopiodelay", obj, "kvm-nopiodelay");
6636 object_property_add_alias(obj, "kvm_mmu", obj, "kvm-mmu");
6637 object_property_add_alias(obj, "kvm_asyncpf", obj, "kvm-asyncpf");
6638 object_property_add_alias(obj, "kvm_asyncpf_int", obj, "kvm-asyncpf-int");
6639 object_property_add_alias(obj, "kvm_steal_time", obj, "kvm-steal-time");
6640 object_property_add_alias(obj, "kvm_pv_eoi", obj, "kvm-pv-eoi");
6641 object_property_add_alias(obj, "kvm_pv_unhalt", obj, "kvm-pv-unhalt");
6642 object_property_add_alias(obj, "kvm_poll_control", obj, "kvm-poll-control");
6643 object_property_add_alias(obj, "svm_lock", obj, "svm-lock");
6644 object_property_add_alias(obj, "nrip_save", obj, "nrip-save");
6645 object_property_add_alias(obj, "tsc_scale", obj, "tsc-scale");
6646 object_property_add_alias(obj, "vmcb_clean", obj, "vmcb-clean");
6647 object_property_add_alias(obj, "pause_filter", obj, "pause-filter");
6648 object_property_add_alias(obj, "sse4_1", obj, "sse4.1");
6649 object_property_add_alias(obj, "sse4_2", obj, "sse4.2");
6651 object_property_add_alias(obj, "hv-apicv", obj, "hv-avic");
6653 if (xcc->model) {
6654 x86_cpu_load_model(cpu, xcc->model);
6658 static int64_t x86_cpu_get_arch_id(CPUState *cs)
6660 X86CPU *cpu = X86_CPU(cs);
6662 return cpu->apic_id;
6665 #if !defined(CONFIG_USER_ONLY)
6666 static bool x86_cpu_get_paging_enabled(const CPUState *cs)
6668 X86CPU *cpu = X86_CPU(cs);
6670 return cpu->env.cr[0] & CR0_PG_MASK;
6672 #endif /* !CONFIG_USER_ONLY */
6674 static void x86_cpu_set_pc(CPUState *cs, vaddr value)
6676 X86CPU *cpu = X86_CPU(cs);
6678 cpu->env.eip = value;
6681 int x86_cpu_pending_interrupt(CPUState *cs, int interrupt_request)
6683 X86CPU *cpu = X86_CPU(cs);
6684 CPUX86State *env = &cpu->env;
6686 #if !defined(CONFIG_USER_ONLY)
6687 if (interrupt_request & CPU_INTERRUPT_POLL) {
6688 return CPU_INTERRUPT_POLL;
6690 #endif
6691 if (interrupt_request & CPU_INTERRUPT_SIPI) {
6692 return CPU_INTERRUPT_SIPI;
6695 if (env->hflags2 & HF2_GIF_MASK) {
6696 if ((interrupt_request & CPU_INTERRUPT_SMI) &&
6697 !(env->hflags & HF_SMM_MASK)) {
6698 return CPU_INTERRUPT_SMI;
6699 } else if ((interrupt_request & CPU_INTERRUPT_NMI) &&
6700 !(env->hflags2 & HF2_NMI_MASK)) {
6701 return CPU_INTERRUPT_NMI;
6702 } else if (interrupt_request & CPU_INTERRUPT_MCE) {
6703 return CPU_INTERRUPT_MCE;
6704 } else if ((interrupt_request & CPU_INTERRUPT_HARD) &&
6705 (((env->hflags2 & HF2_VINTR_MASK) &&
6706 (env->hflags2 & HF2_HIF_MASK)) ||
6707 (!(env->hflags2 & HF2_VINTR_MASK) &&
6708 (env->eflags & IF_MASK &&
6709 !(env->hflags & HF_INHIBIT_IRQ_MASK))))) {
6710 return CPU_INTERRUPT_HARD;
6711 #if !defined(CONFIG_USER_ONLY)
6712 } else if (env->hflags2 & HF2_VGIF_MASK) {
6713 if((interrupt_request & CPU_INTERRUPT_VIRQ) &&
6714 (env->eflags & IF_MASK) &&
6715 !(env->hflags & HF_INHIBIT_IRQ_MASK)) {
6716 return CPU_INTERRUPT_VIRQ;
6718 #endif
6722 return 0;
6725 static bool x86_cpu_has_work(CPUState *cs)
6727 return x86_cpu_pending_interrupt(cs, cs->interrupt_request) != 0;
6730 static void x86_disas_set_info(CPUState *cs, disassemble_info *info)
6732 X86CPU *cpu = X86_CPU(cs);
6733 CPUX86State *env = &cpu->env;
6735 info->mach = (env->hflags & HF_CS64_MASK ? bfd_mach_x86_64
6736 : env->hflags & HF_CS32_MASK ? bfd_mach_i386_i386
6737 : bfd_mach_i386_i8086);
6738 info->print_insn = print_insn_i386;
6740 info->cap_arch = CS_ARCH_X86;
6741 info->cap_mode = (env->hflags & HF_CS64_MASK ? CS_MODE_64
6742 : env->hflags & HF_CS32_MASK ? CS_MODE_32
6743 : CS_MODE_16);
6744 info->cap_insn_unit = 1;
6745 info->cap_insn_split = 8;
6748 void x86_update_hflags(CPUX86State *env)
6750 uint32_t hflags;
6751 #define HFLAG_COPY_MASK \
6752 ~( HF_CPL_MASK | HF_PE_MASK | HF_MP_MASK | HF_EM_MASK | \
6753 HF_TS_MASK | HF_TF_MASK | HF_VM_MASK | HF_IOPL_MASK | \
6754 HF_OSFXSR_MASK | HF_LMA_MASK | HF_CS32_MASK | \
6755 HF_SS32_MASK | HF_CS64_MASK | HF_ADDSEG_MASK)
6757 hflags = env->hflags & HFLAG_COPY_MASK;
6758 hflags |= (env->segs[R_SS].flags >> DESC_DPL_SHIFT) & HF_CPL_MASK;
6759 hflags |= (env->cr[0] & CR0_PE_MASK) << (HF_PE_SHIFT - CR0_PE_SHIFT);
6760 hflags |= (env->cr[0] << (HF_MP_SHIFT - CR0_MP_SHIFT)) &
6761 (HF_MP_MASK | HF_EM_MASK | HF_TS_MASK);
6762 hflags |= (env->eflags & (HF_TF_MASK | HF_VM_MASK | HF_IOPL_MASK));
6764 if (env->cr[4] & CR4_OSFXSR_MASK) {
6765 hflags |= HF_OSFXSR_MASK;
6768 if (env->efer & MSR_EFER_LMA) {
6769 hflags |= HF_LMA_MASK;
6772 if ((hflags & HF_LMA_MASK) && (env->segs[R_CS].flags & DESC_L_MASK)) {
6773 hflags |= HF_CS32_MASK | HF_SS32_MASK | HF_CS64_MASK;
6774 } else {
6775 hflags |= (env->segs[R_CS].flags & DESC_B_MASK) >>
6776 (DESC_B_SHIFT - HF_CS32_SHIFT);
6777 hflags |= (env->segs[R_SS].flags & DESC_B_MASK) >>
6778 (DESC_B_SHIFT - HF_SS32_SHIFT);
6779 if (!(env->cr[0] & CR0_PE_MASK) || (env->eflags & VM_MASK) ||
6780 !(hflags & HF_CS32_MASK)) {
6781 hflags |= HF_ADDSEG_MASK;
6782 } else {
6783 hflags |= ((env->segs[R_DS].base | env->segs[R_ES].base |
6784 env->segs[R_SS].base) != 0) << HF_ADDSEG_SHIFT;
6787 env->hflags = hflags;
6790 static Property x86_cpu_properties[] = {
6791 #ifdef CONFIG_USER_ONLY
6792 /* apic_id = 0 by default for *-user, see commit 9886e834 */
6793 DEFINE_PROP_UINT32("apic-id", X86CPU, apic_id, 0),
6794 DEFINE_PROP_INT32("thread-id", X86CPU, thread_id, 0),
6795 DEFINE_PROP_INT32("core-id", X86CPU, core_id, 0),
6796 DEFINE_PROP_INT32("die-id", X86CPU, die_id, 0),
6797 DEFINE_PROP_INT32("socket-id", X86CPU, socket_id, 0),
6798 #else
6799 DEFINE_PROP_UINT32("apic-id", X86CPU, apic_id, UNASSIGNED_APIC_ID),
6800 DEFINE_PROP_INT32("thread-id", X86CPU, thread_id, -1),
6801 DEFINE_PROP_INT32("core-id", X86CPU, core_id, -1),
6802 DEFINE_PROP_INT32("die-id", X86CPU, die_id, -1),
6803 DEFINE_PROP_INT32("socket-id", X86CPU, socket_id, -1),
6804 #endif
6805 DEFINE_PROP_INT32("node-id", X86CPU, node_id, CPU_UNSET_NUMA_NODE_ID),
6806 DEFINE_PROP_BOOL("pmu", X86CPU, enable_pmu, false),
6808 DEFINE_PROP_UINT32("hv-spinlocks", X86CPU, hyperv_spinlock_attempts,
6809 HYPERV_SPINLOCK_NEVER_NOTIFY),
6810 DEFINE_PROP_BIT64("hv-relaxed", X86CPU, hyperv_features,
6811 HYPERV_FEAT_RELAXED, 0),
6812 DEFINE_PROP_BIT64("hv-vapic", X86CPU, hyperv_features,
6813 HYPERV_FEAT_VAPIC, 0),
6814 DEFINE_PROP_BIT64("hv-time", X86CPU, hyperv_features,
6815 HYPERV_FEAT_TIME, 0),
6816 DEFINE_PROP_BIT64("hv-crash", X86CPU, hyperv_features,
6817 HYPERV_FEAT_CRASH, 0),
6818 DEFINE_PROP_BIT64("hv-reset", X86CPU, hyperv_features,
6819 HYPERV_FEAT_RESET, 0),
6820 DEFINE_PROP_BIT64("hv-vpindex", X86CPU, hyperv_features,
6821 HYPERV_FEAT_VPINDEX, 0),
6822 DEFINE_PROP_BIT64("hv-runtime", X86CPU, hyperv_features,
6823 HYPERV_FEAT_RUNTIME, 0),
6824 DEFINE_PROP_BIT64("hv-synic", X86CPU, hyperv_features,
6825 HYPERV_FEAT_SYNIC, 0),
6826 DEFINE_PROP_BIT64("hv-stimer", X86CPU, hyperv_features,
6827 HYPERV_FEAT_STIMER, 0),
6828 DEFINE_PROP_BIT64("hv-frequencies", X86CPU, hyperv_features,
6829 HYPERV_FEAT_FREQUENCIES, 0),
6830 DEFINE_PROP_BIT64("hv-reenlightenment", X86CPU, hyperv_features,
6831 HYPERV_FEAT_REENLIGHTENMENT, 0),
6832 DEFINE_PROP_BIT64("hv-tlbflush", X86CPU, hyperv_features,
6833 HYPERV_FEAT_TLBFLUSH, 0),
6834 DEFINE_PROP_BIT64("hv-evmcs", X86CPU, hyperv_features,
6835 HYPERV_FEAT_EVMCS, 0),
6836 DEFINE_PROP_BIT64("hv-ipi", X86CPU, hyperv_features,
6837 HYPERV_FEAT_IPI, 0),
6838 DEFINE_PROP_BIT64("hv-stimer-direct", X86CPU, hyperv_features,
6839 HYPERV_FEAT_STIMER_DIRECT, 0),
6840 DEFINE_PROP_BIT64("hv-avic", X86CPU, hyperv_features,
6841 HYPERV_FEAT_AVIC, 0),
6842 DEFINE_PROP_ON_OFF_AUTO("hv-no-nonarch-coresharing", X86CPU,
6843 hyperv_no_nonarch_cs, ON_OFF_AUTO_OFF),
6844 DEFINE_PROP_BOOL("hv-passthrough", X86CPU, hyperv_passthrough, false),
6845 DEFINE_PROP_BOOL("hv-enforce-cpuid", X86CPU, hyperv_enforce_cpuid, false),
6847 /* WS2008R2 identify by default */
6848 DEFINE_PROP_UINT32("hv-version-id-build", X86CPU, hyperv_ver_id_build,
6849 0x3839),
6850 DEFINE_PROP_UINT16("hv-version-id-major", X86CPU, hyperv_ver_id_major,
6851 0x000A),
6852 DEFINE_PROP_UINT16("hv-version-id-minor", X86CPU, hyperv_ver_id_minor,
6853 0x0000),
6854 DEFINE_PROP_UINT32("hv-version-id-spack", X86CPU, hyperv_ver_id_sp, 0),
6855 DEFINE_PROP_UINT8("hv-version-id-sbranch", X86CPU, hyperv_ver_id_sb, 0),
6856 DEFINE_PROP_UINT32("hv-version-id-snumber", X86CPU, hyperv_ver_id_sn, 0),
6858 DEFINE_PROP_BOOL("check", X86CPU, check_cpuid, true),
6859 DEFINE_PROP_BOOL("enforce", X86CPU, enforce_cpuid, false),
6860 DEFINE_PROP_BOOL("x-force-features", X86CPU, force_features, false),
6861 DEFINE_PROP_BOOL("kvm", X86CPU, expose_kvm, true),
6862 DEFINE_PROP_UINT32("phys-bits", X86CPU, phys_bits, 0),
6863 DEFINE_PROP_BOOL("host-phys-bits", X86CPU, host_phys_bits, false),
6864 DEFINE_PROP_UINT8("host-phys-bits-limit", X86CPU, host_phys_bits_limit, 0),
6865 DEFINE_PROP_BOOL("fill-mtrr-mask", X86CPU, fill_mtrr_mask, true),
6866 DEFINE_PROP_UINT32("level-func7", X86CPU, env.cpuid_level_func7,
6867 UINT32_MAX),
6868 DEFINE_PROP_UINT32("level", X86CPU, env.cpuid_level, UINT32_MAX),
6869 DEFINE_PROP_UINT32("xlevel", X86CPU, env.cpuid_xlevel, UINT32_MAX),
6870 DEFINE_PROP_UINT32("xlevel2", X86CPU, env.cpuid_xlevel2, UINT32_MAX),
6871 DEFINE_PROP_UINT32("min-level", X86CPU, env.cpuid_min_level, 0),
6872 DEFINE_PROP_UINT32("min-xlevel", X86CPU, env.cpuid_min_xlevel, 0),
6873 DEFINE_PROP_UINT32("min-xlevel2", X86CPU, env.cpuid_min_xlevel2, 0),
6874 DEFINE_PROP_UINT64("ucode-rev", X86CPU, ucode_rev, 0),
6875 DEFINE_PROP_BOOL("full-cpuid-auto-level", X86CPU, full_cpuid_auto_level, true),
6876 DEFINE_PROP_STRING("hv-vendor-id", X86CPU, hyperv_vendor),
6877 DEFINE_PROP_BOOL("cpuid-0xb", X86CPU, enable_cpuid_0xb, true),
6878 DEFINE_PROP_BOOL("x-vendor-cpuid-only", X86CPU, vendor_cpuid_only, true),
6879 DEFINE_PROP_BOOL("lmce", X86CPU, enable_lmce, false),
6880 DEFINE_PROP_BOOL("l3-cache", X86CPU, enable_l3_cache, true),
6881 DEFINE_PROP_BOOL("kvm-no-smi-migration", X86CPU, kvm_no_smi_migration,
6882 false),
6883 DEFINE_PROP_BOOL("kvm-pv-enforce-cpuid", X86CPU, kvm_pv_enforce_cpuid,
6884 false),
6885 DEFINE_PROP_BOOL("vmware-cpuid-freq", X86CPU, vmware_cpuid_freq, true),
6886 DEFINE_PROP_BOOL("tcg-cpuid", X86CPU, expose_tcg, true),
6887 DEFINE_PROP_BOOL("x-migrate-smi-count", X86CPU, migrate_smi_count,
6888 true),
6890 * lecacy_cache defaults to true unless the CPU model provides its
6891 * own cache information (see x86_cpu_load_def()).
6893 DEFINE_PROP_BOOL("legacy-cache", X86CPU, legacy_cache, true),
6896 * From "Requirements for Implementing the Microsoft
6897 * Hypervisor Interface":
6898 * https://docs.microsoft.com/en-us/virtualization/hyper-v-on-windows/reference/tlfs
6900 * "Starting with Windows Server 2012 and Windows 8, if
6901 * CPUID.40000005.EAX contains a value of -1, Windows assumes that
6902 * the hypervisor imposes no specific limit to the number of VPs.
6903 * In this case, Windows Server 2012 guest VMs may use more than
6904 * 64 VPs, up to the maximum supported number of processors applicable
6905 * to the specific Windows version being used."
6907 DEFINE_PROP_INT32("x-hv-max-vps", X86CPU, hv_max_vps, -1),
6908 DEFINE_PROP_BOOL("x-hv-synic-kvm-only", X86CPU, hyperv_synic_kvm_only,
6909 false),
6910 DEFINE_PROP_BOOL("x-intel-pt-auto-level", X86CPU, intel_pt_auto_level,
6911 true),
6912 DEFINE_PROP_END_OF_LIST()
6915 #ifndef CONFIG_USER_ONLY
6916 #include "hw/core/sysemu-cpu-ops.h"
6918 static const struct SysemuCPUOps i386_sysemu_ops = {
6919 .get_memory_mapping = x86_cpu_get_memory_mapping,
6920 .get_paging_enabled = x86_cpu_get_paging_enabled,
6921 .get_phys_page_attrs_debug = x86_cpu_get_phys_page_attrs_debug,
6922 .asidx_from_attrs = x86_asidx_from_attrs,
6923 .get_crash_info = x86_cpu_get_crash_info,
6924 .write_elf32_note = x86_cpu_write_elf32_note,
6925 .write_elf64_note = x86_cpu_write_elf64_note,
6926 .write_elf32_qemunote = x86_cpu_write_elf32_qemunote,
6927 .write_elf64_qemunote = x86_cpu_write_elf64_qemunote,
6928 .legacy_vmsd = &vmstate_x86_cpu,
6930 #endif
6932 static void x86_cpu_common_class_init(ObjectClass *oc, void *data)
6934 X86CPUClass *xcc = X86_CPU_CLASS(oc);
6935 CPUClass *cc = CPU_CLASS(oc);
6936 DeviceClass *dc = DEVICE_CLASS(oc);
6937 FeatureWord w;
6939 device_class_set_parent_realize(dc, x86_cpu_realizefn,
6940 &xcc->parent_realize);
6941 device_class_set_parent_unrealize(dc, x86_cpu_unrealizefn,
6942 &xcc->parent_unrealize);
6943 device_class_set_props(dc, x86_cpu_properties);
6945 device_class_set_parent_reset(dc, x86_cpu_reset, &xcc->parent_reset);
6946 cc->reset_dump_flags = CPU_DUMP_FPU | CPU_DUMP_CCOP;
6948 cc->class_by_name = x86_cpu_class_by_name;
6949 cc->parse_features = x86_cpu_parse_featurestr;
6950 cc->has_work = x86_cpu_has_work;
6951 cc->dump_state = x86_cpu_dump_state;
6952 cc->set_pc = x86_cpu_set_pc;
6953 cc->gdb_read_register = x86_cpu_gdb_read_register;
6954 cc->gdb_write_register = x86_cpu_gdb_write_register;
6955 cc->get_arch_id = x86_cpu_get_arch_id;
6957 #ifndef CONFIG_USER_ONLY
6958 cc->sysemu_ops = &i386_sysemu_ops;
6959 #endif /* !CONFIG_USER_ONLY */
6961 cc->gdb_arch_name = x86_gdb_arch_name;
6962 #ifdef TARGET_X86_64
6963 cc->gdb_core_xml_file = "i386-64bit.xml";
6964 cc->gdb_num_core_regs = 66;
6965 #else
6966 cc->gdb_core_xml_file = "i386-32bit.xml";
6967 cc->gdb_num_core_regs = 50;
6968 #endif
6969 cc->disas_set_info = x86_disas_set_info;
6971 dc->user_creatable = true;
6973 object_class_property_add(oc, "family", "int",
6974 x86_cpuid_version_get_family,
6975 x86_cpuid_version_set_family, NULL, NULL);
6976 object_class_property_add(oc, "model", "int",
6977 x86_cpuid_version_get_model,
6978 x86_cpuid_version_set_model, NULL, NULL);
6979 object_class_property_add(oc, "stepping", "int",
6980 x86_cpuid_version_get_stepping,
6981 x86_cpuid_version_set_stepping, NULL, NULL);
6982 object_class_property_add_str(oc, "vendor",
6983 x86_cpuid_get_vendor,
6984 x86_cpuid_set_vendor);
6985 object_class_property_add_str(oc, "model-id",
6986 x86_cpuid_get_model_id,
6987 x86_cpuid_set_model_id);
6988 object_class_property_add(oc, "tsc-frequency", "int",
6989 x86_cpuid_get_tsc_freq,
6990 x86_cpuid_set_tsc_freq, NULL, NULL);
6992 * The "unavailable-features" property has the same semantics as
6993 * CpuDefinitionInfo.unavailable-features on the "query-cpu-definitions"
6994 * QMP command: they list the features that would have prevented the
6995 * CPU from running if the "enforce" flag was set.
6997 object_class_property_add(oc, "unavailable-features", "strList",
6998 x86_cpu_get_unavailable_features,
6999 NULL, NULL, NULL);
7001 #if !defined(CONFIG_USER_ONLY)
7002 object_class_property_add(oc, "crash-information", "GuestPanicInformation",
7003 x86_cpu_get_crash_info_qom, NULL, NULL, NULL);
7004 #endif
7006 for (w = 0; w < FEATURE_WORDS; w++) {
7007 int bitnr;
7008 for (bitnr = 0; bitnr < 64; bitnr++) {
7009 x86_cpu_register_feature_bit_props(xcc, w, bitnr);
7014 static const TypeInfo x86_cpu_type_info = {
7015 .name = TYPE_X86_CPU,
7016 .parent = TYPE_CPU,
7017 .instance_size = sizeof(X86CPU),
7018 .instance_init = x86_cpu_initfn,
7019 .instance_post_init = x86_cpu_post_initfn,
7021 .abstract = true,
7022 .class_size = sizeof(X86CPUClass),
7023 .class_init = x86_cpu_common_class_init,
7026 /* "base" CPU model, used by query-cpu-model-expansion */
7027 static void x86_cpu_base_class_init(ObjectClass *oc, void *data)
7029 X86CPUClass *xcc = X86_CPU_CLASS(oc);
7031 xcc->static_model = true;
7032 xcc->migration_safe = true;
7033 xcc->model_description = "base CPU model type with no features enabled";
7034 xcc->ordering = 8;
7037 static const TypeInfo x86_base_cpu_type_info = {
7038 .name = X86_CPU_TYPE_NAME("base"),
7039 .parent = TYPE_X86_CPU,
7040 .class_init = x86_cpu_base_class_init,
7043 static void x86_cpu_register_types(void)
7045 int i;
7047 type_register_static(&x86_cpu_type_info);
7048 for (i = 0; i < ARRAY_SIZE(builtin_x86_defs); i++) {
7049 x86_register_cpudef_types(&builtin_x86_defs[i]);
7051 type_register_static(&max_x86_cpu_type_info);
7052 type_register_static(&x86_base_cpu_type_info);
7055 type_init(x86_cpu_register_types)