spapr_numa.c: handle auto NUMA node with no distance info
[qemu.git] / target / i386 / cpu.c
blob6b029f1bdf165f1b9ef3bb63eb6e5a1991266e4f
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_i386.h"
30 #include "qapi/qapi-visit-machine.h"
31 #include "qapi/qmp/qerror.h"
32 #include "qapi/qapi-commands-machine-target.h"
33 #include "standard-headers/asm-x86/kvm_para.h"
34 #include "hw/qdev-properties.h"
35 #include "hw/i386/topology.h"
36 #ifndef CONFIG_USER_ONLY
37 #include "exec/address-spaces.h"
38 #include "hw/boards.h"
39 #endif
41 #include "disas/capstone.h"
42 #include "cpu-internal.h"
44 /* Helpers for building CPUID[2] descriptors: */
46 struct CPUID2CacheDescriptorInfo {
47 enum CacheType type;
48 int level;
49 int size;
50 int line_size;
51 int associativity;
55 * Known CPUID 2 cache descriptors.
56 * From Intel SDM Volume 2A, CPUID instruction
58 struct CPUID2CacheDescriptorInfo cpuid2_cache_descriptors[] = {
59 [0x06] = { .level = 1, .type = INSTRUCTION_CACHE, .size = 8 * KiB,
60 .associativity = 4, .line_size = 32, },
61 [0x08] = { .level = 1, .type = INSTRUCTION_CACHE, .size = 16 * KiB,
62 .associativity = 4, .line_size = 32, },
63 [0x09] = { .level = 1, .type = INSTRUCTION_CACHE, .size = 32 * KiB,
64 .associativity = 4, .line_size = 64, },
65 [0x0A] = { .level = 1, .type = DATA_CACHE, .size = 8 * KiB,
66 .associativity = 2, .line_size = 32, },
67 [0x0C] = { .level = 1, .type = DATA_CACHE, .size = 16 * KiB,
68 .associativity = 4, .line_size = 32, },
69 [0x0D] = { .level = 1, .type = DATA_CACHE, .size = 16 * KiB,
70 .associativity = 4, .line_size = 64, },
71 [0x0E] = { .level = 1, .type = DATA_CACHE, .size = 24 * KiB,
72 .associativity = 6, .line_size = 64, },
73 [0x1D] = { .level = 2, .type = UNIFIED_CACHE, .size = 128 * KiB,
74 .associativity = 2, .line_size = 64, },
75 [0x21] = { .level = 2, .type = UNIFIED_CACHE, .size = 256 * KiB,
76 .associativity = 8, .line_size = 64, },
77 /* lines per sector is not supported cpuid2_cache_descriptor(),
78 * so descriptors 0x22, 0x23 are not included
80 [0x24] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
81 .associativity = 16, .line_size = 64, },
82 /* lines per sector is not supported cpuid2_cache_descriptor(),
83 * so descriptors 0x25, 0x20 are not included
85 [0x2C] = { .level = 1, .type = DATA_CACHE, .size = 32 * KiB,
86 .associativity = 8, .line_size = 64, },
87 [0x30] = { .level = 1, .type = INSTRUCTION_CACHE, .size = 32 * KiB,
88 .associativity = 8, .line_size = 64, },
89 [0x41] = { .level = 2, .type = UNIFIED_CACHE, .size = 128 * KiB,
90 .associativity = 4, .line_size = 32, },
91 [0x42] = { .level = 2, .type = UNIFIED_CACHE, .size = 256 * KiB,
92 .associativity = 4, .line_size = 32, },
93 [0x43] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
94 .associativity = 4, .line_size = 32, },
95 [0x44] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
96 .associativity = 4, .line_size = 32, },
97 [0x45] = { .level = 2, .type = UNIFIED_CACHE, .size = 2 * MiB,
98 .associativity = 4, .line_size = 32, },
99 [0x46] = { .level = 3, .type = UNIFIED_CACHE, .size = 4 * MiB,
100 .associativity = 4, .line_size = 64, },
101 [0x47] = { .level = 3, .type = UNIFIED_CACHE, .size = 8 * MiB,
102 .associativity = 8, .line_size = 64, },
103 [0x48] = { .level = 2, .type = UNIFIED_CACHE, .size = 3 * MiB,
104 .associativity = 12, .line_size = 64, },
105 /* Descriptor 0x49 depends on CPU family/model, so it is not included */
106 [0x4A] = { .level = 3, .type = UNIFIED_CACHE, .size = 6 * MiB,
107 .associativity = 12, .line_size = 64, },
108 [0x4B] = { .level = 3, .type = UNIFIED_CACHE, .size = 8 * MiB,
109 .associativity = 16, .line_size = 64, },
110 [0x4C] = { .level = 3, .type = UNIFIED_CACHE, .size = 12 * MiB,
111 .associativity = 12, .line_size = 64, },
112 [0x4D] = { .level = 3, .type = UNIFIED_CACHE, .size = 16 * MiB,
113 .associativity = 16, .line_size = 64, },
114 [0x4E] = { .level = 2, .type = UNIFIED_CACHE, .size = 6 * MiB,
115 .associativity = 24, .line_size = 64, },
116 [0x60] = { .level = 1, .type = DATA_CACHE, .size = 16 * KiB,
117 .associativity = 8, .line_size = 64, },
118 [0x66] = { .level = 1, .type = DATA_CACHE, .size = 8 * KiB,
119 .associativity = 4, .line_size = 64, },
120 [0x67] = { .level = 1, .type = DATA_CACHE, .size = 16 * KiB,
121 .associativity = 4, .line_size = 64, },
122 [0x68] = { .level = 1, .type = DATA_CACHE, .size = 32 * KiB,
123 .associativity = 4, .line_size = 64, },
124 [0x78] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
125 .associativity = 4, .line_size = 64, },
126 /* lines per sector is not supported cpuid2_cache_descriptor(),
127 * so descriptors 0x79, 0x7A, 0x7B, 0x7C are not included.
129 [0x7D] = { .level = 2, .type = UNIFIED_CACHE, .size = 2 * MiB,
130 .associativity = 8, .line_size = 64, },
131 [0x7F] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
132 .associativity = 2, .line_size = 64, },
133 [0x80] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
134 .associativity = 8, .line_size = 64, },
135 [0x82] = { .level = 2, .type = UNIFIED_CACHE, .size = 256 * KiB,
136 .associativity = 8, .line_size = 32, },
137 [0x83] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
138 .associativity = 8, .line_size = 32, },
139 [0x84] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
140 .associativity = 8, .line_size = 32, },
141 [0x85] = { .level = 2, .type = UNIFIED_CACHE, .size = 2 * MiB,
142 .associativity = 8, .line_size = 32, },
143 [0x86] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
144 .associativity = 4, .line_size = 64, },
145 [0x87] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
146 .associativity = 8, .line_size = 64, },
147 [0xD0] = { .level = 3, .type = UNIFIED_CACHE, .size = 512 * KiB,
148 .associativity = 4, .line_size = 64, },
149 [0xD1] = { .level = 3, .type = UNIFIED_CACHE, .size = 1 * MiB,
150 .associativity = 4, .line_size = 64, },
151 [0xD2] = { .level = 3, .type = UNIFIED_CACHE, .size = 2 * MiB,
152 .associativity = 4, .line_size = 64, },
153 [0xD6] = { .level = 3, .type = UNIFIED_CACHE, .size = 1 * MiB,
154 .associativity = 8, .line_size = 64, },
155 [0xD7] = { .level = 3, .type = UNIFIED_CACHE, .size = 2 * MiB,
156 .associativity = 8, .line_size = 64, },
157 [0xD8] = { .level = 3, .type = UNIFIED_CACHE, .size = 4 * MiB,
158 .associativity = 8, .line_size = 64, },
159 [0xDC] = { .level = 3, .type = UNIFIED_CACHE, .size = 1.5 * MiB,
160 .associativity = 12, .line_size = 64, },
161 [0xDD] = { .level = 3, .type = UNIFIED_CACHE, .size = 3 * MiB,
162 .associativity = 12, .line_size = 64, },
163 [0xDE] = { .level = 3, .type = UNIFIED_CACHE, .size = 6 * MiB,
164 .associativity = 12, .line_size = 64, },
165 [0xE2] = { .level = 3, .type = UNIFIED_CACHE, .size = 2 * MiB,
166 .associativity = 16, .line_size = 64, },
167 [0xE3] = { .level = 3, .type = UNIFIED_CACHE, .size = 4 * MiB,
168 .associativity = 16, .line_size = 64, },
169 [0xE4] = { .level = 3, .type = UNIFIED_CACHE, .size = 8 * MiB,
170 .associativity = 16, .line_size = 64, },
171 [0xEA] = { .level = 3, .type = UNIFIED_CACHE, .size = 12 * MiB,
172 .associativity = 24, .line_size = 64, },
173 [0xEB] = { .level = 3, .type = UNIFIED_CACHE, .size = 18 * MiB,
174 .associativity = 24, .line_size = 64, },
175 [0xEC] = { .level = 3, .type = UNIFIED_CACHE, .size = 24 * MiB,
176 .associativity = 24, .line_size = 64, },
180 * "CPUID leaf 2 does not report cache descriptor information,
181 * use CPUID leaf 4 to query cache parameters"
183 #define CACHE_DESCRIPTOR_UNAVAILABLE 0xFF
186 * Return a CPUID 2 cache descriptor for a given cache.
187 * If no known descriptor is found, return CACHE_DESCRIPTOR_UNAVAILABLE
189 static uint8_t cpuid2_cache_descriptor(CPUCacheInfo *cache)
191 int i;
193 assert(cache->size > 0);
194 assert(cache->level > 0);
195 assert(cache->line_size > 0);
196 assert(cache->associativity > 0);
197 for (i = 0; i < ARRAY_SIZE(cpuid2_cache_descriptors); i++) {
198 struct CPUID2CacheDescriptorInfo *d = &cpuid2_cache_descriptors[i];
199 if (d->level == cache->level && d->type == cache->type &&
200 d->size == cache->size && d->line_size == cache->line_size &&
201 d->associativity == cache->associativity) {
202 return i;
206 return CACHE_DESCRIPTOR_UNAVAILABLE;
209 /* CPUID Leaf 4 constants: */
211 /* EAX: */
212 #define CACHE_TYPE_D 1
213 #define CACHE_TYPE_I 2
214 #define CACHE_TYPE_UNIFIED 3
216 #define CACHE_LEVEL(l) (l << 5)
218 #define CACHE_SELF_INIT_LEVEL (1 << 8)
220 /* EDX: */
221 #define CACHE_NO_INVD_SHARING (1 << 0)
222 #define CACHE_INCLUSIVE (1 << 1)
223 #define CACHE_COMPLEX_IDX (1 << 2)
225 /* Encode CacheType for CPUID[4].EAX */
226 #define CACHE_TYPE(t) (((t) == DATA_CACHE) ? CACHE_TYPE_D : \
227 ((t) == INSTRUCTION_CACHE) ? CACHE_TYPE_I : \
228 ((t) == UNIFIED_CACHE) ? CACHE_TYPE_UNIFIED : \
229 0 /* Invalid value */)
232 /* Encode cache info for CPUID[4] */
233 static void encode_cache_cpuid4(CPUCacheInfo *cache,
234 int num_apic_ids, int num_cores,
235 uint32_t *eax, uint32_t *ebx,
236 uint32_t *ecx, uint32_t *edx)
238 assert(cache->size == cache->line_size * cache->associativity *
239 cache->partitions * cache->sets);
241 assert(num_apic_ids > 0);
242 *eax = CACHE_TYPE(cache->type) |
243 CACHE_LEVEL(cache->level) |
244 (cache->self_init ? CACHE_SELF_INIT_LEVEL : 0) |
245 ((num_cores - 1) << 26) |
246 ((num_apic_ids - 1) << 14);
248 assert(cache->line_size > 0);
249 assert(cache->partitions > 0);
250 assert(cache->associativity > 0);
251 /* We don't implement fully-associative caches */
252 assert(cache->associativity < cache->sets);
253 *ebx = (cache->line_size - 1) |
254 ((cache->partitions - 1) << 12) |
255 ((cache->associativity - 1) << 22);
257 assert(cache->sets > 0);
258 *ecx = cache->sets - 1;
260 *edx = (cache->no_invd_sharing ? CACHE_NO_INVD_SHARING : 0) |
261 (cache->inclusive ? CACHE_INCLUSIVE : 0) |
262 (cache->complex_indexing ? CACHE_COMPLEX_IDX : 0);
265 /* Encode cache info for CPUID[0x80000005].ECX or CPUID[0x80000005].EDX */
266 static uint32_t encode_cache_cpuid80000005(CPUCacheInfo *cache)
268 assert(cache->size % 1024 == 0);
269 assert(cache->lines_per_tag > 0);
270 assert(cache->associativity > 0);
271 assert(cache->line_size > 0);
272 return ((cache->size / 1024) << 24) | (cache->associativity << 16) |
273 (cache->lines_per_tag << 8) | (cache->line_size);
276 #define ASSOC_FULL 0xFF
278 /* AMD associativity encoding used on CPUID Leaf 0x80000006: */
279 #define AMD_ENC_ASSOC(a) (a <= 1 ? a : \
280 a == 2 ? 0x2 : \
281 a == 4 ? 0x4 : \
282 a == 8 ? 0x6 : \
283 a == 16 ? 0x8 : \
284 a == 32 ? 0xA : \
285 a == 48 ? 0xB : \
286 a == 64 ? 0xC : \
287 a == 96 ? 0xD : \
288 a == 128 ? 0xE : \
289 a == ASSOC_FULL ? 0xF : \
290 0 /* invalid value */)
293 * Encode cache info for CPUID[0x80000006].ECX and CPUID[0x80000006].EDX
294 * @l3 can be NULL.
296 static void encode_cache_cpuid80000006(CPUCacheInfo *l2,
297 CPUCacheInfo *l3,
298 uint32_t *ecx, uint32_t *edx)
300 assert(l2->size % 1024 == 0);
301 assert(l2->associativity > 0);
302 assert(l2->lines_per_tag > 0);
303 assert(l2->line_size > 0);
304 *ecx = ((l2->size / 1024) << 16) |
305 (AMD_ENC_ASSOC(l2->associativity) << 12) |
306 (l2->lines_per_tag << 8) | (l2->line_size);
308 if (l3) {
309 assert(l3->size % (512 * 1024) == 0);
310 assert(l3->associativity > 0);
311 assert(l3->lines_per_tag > 0);
312 assert(l3->line_size > 0);
313 *edx = ((l3->size / (512 * 1024)) << 18) |
314 (AMD_ENC_ASSOC(l3->associativity) << 12) |
315 (l3->lines_per_tag << 8) | (l3->line_size);
316 } else {
317 *edx = 0;
321 /* Encode cache info for CPUID[8000001D] */
322 static void encode_cache_cpuid8000001d(CPUCacheInfo *cache,
323 X86CPUTopoInfo *topo_info,
324 uint32_t *eax, uint32_t *ebx,
325 uint32_t *ecx, uint32_t *edx)
327 uint32_t l3_threads;
328 assert(cache->size == cache->line_size * cache->associativity *
329 cache->partitions * cache->sets);
331 *eax = CACHE_TYPE(cache->type) | CACHE_LEVEL(cache->level) |
332 (cache->self_init ? CACHE_SELF_INIT_LEVEL : 0);
334 /* L3 is shared among multiple cores */
335 if (cache->level == 3) {
336 l3_threads = topo_info->cores_per_die * topo_info->threads_per_core;
337 *eax |= (l3_threads - 1) << 14;
338 } else {
339 *eax |= ((topo_info->threads_per_core - 1) << 14);
342 assert(cache->line_size > 0);
343 assert(cache->partitions > 0);
344 assert(cache->associativity > 0);
345 /* We don't implement fully-associative caches */
346 assert(cache->associativity < cache->sets);
347 *ebx = (cache->line_size - 1) |
348 ((cache->partitions - 1) << 12) |
349 ((cache->associativity - 1) << 22);
351 assert(cache->sets > 0);
352 *ecx = cache->sets - 1;
354 *edx = (cache->no_invd_sharing ? CACHE_NO_INVD_SHARING : 0) |
355 (cache->inclusive ? CACHE_INCLUSIVE : 0) |
356 (cache->complex_indexing ? CACHE_COMPLEX_IDX : 0);
359 /* Encode cache info for CPUID[8000001E] */
360 static void encode_topo_cpuid8000001e(X86CPU *cpu, X86CPUTopoInfo *topo_info,
361 uint32_t *eax, uint32_t *ebx,
362 uint32_t *ecx, uint32_t *edx)
364 X86CPUTopoIDs topo_ids;
366 x86_topo_ids_from_apicid(cpu->apic_id, topo_info, &topo_ids);
368 *eax = cpu->apic_id;
371 * CPUID_Fn8000001E_EBX [Core Identifiers] (CoreId)
372 * Read-only. Reset: 0000_XXXXh.
373 * See Core::X86::Cpuid::ExtApicId.
374 * Core::X86::Cpuid::CoreId_lthree[1:0]_core[3:0]_thread[1:0];
375 * Bits Description
376 * 31:16 Reserved.
377 * 15:8 ThreadsPerCore: threads per core. Read-only. Reset: XXh.
378 * The number of threads per core is ThreadsPerCore+1.
379 * 7:0 CoreId: core ID. Read-only. Reset: XXh.
381 * NOTE: CoreId is already part of apic_id. Just use it. We can
382 * use all the 8 bits to represent the core_id here.
384 *ebx = ((topo_info->threads_per_core - 1) << 8) | (topo_ids.core_id & 0xFF);
387 * CPUID_Fn8000001E_ECX [Node Identifiers] (NodeId)
388 * Read-only. Reset: 0000_0XXXh.
389 * Core::X86::Cpuid::NodeId_lthree[1:0]_core[3:0]_thread[1:0];
390 * Bits Description
391 * 31:11 Reserved.
392 * 10:8 NodesPerProcessor: Node per processor. Read-only. Reset: XXXb.
393 * ValidValues:
394 * Value Description
395 * 000b 1 node per processor.
396 * 001b 2 nodes per processor.
397 * 010b Reserved.
398 * 011b 4 nodes per processor.
399 * 111b-100b Reserved.
400 * 7:0 NodeId: Node ID. Read-only. Reset: XXh.
402 * NOTE: Hardware reserves 3 bits for number of nodes per processor.
403 * But users can create more nodes than the actual hardware can
404 * support. To genaralize we can use all the upper 8 bits for nodes.
405 * NodeId is combination of node and socket_id which is already decoded
406 * in apic_id. Just use it by shifting.
408 *ecx = ((topo_info->dies_per_pkg - 1) << 8) |
409 ((cpu->apic_id >> apicid_die_offset(topo_info)) & 0xFF);
411 *edx = 0;
415 * Definitions of the hardcoded cache entries we expose:
416 * These are legacy cache values. If there is a need to change any
417 * of these values please use builtin_x86_defs
420 /* L1 data cache: */
421 static CPUCacheInfo legacy_l1d_cache = {
422 .type = DATA_CACHE,
423 .level = 1,
424 .size = 32 * KiB,
425 .self_init = 1,
426 .line_size = 64,
427 .associativity = 8,
428 .sets = 64,
429 .partitions = 1,
430 .no_invd_sharing = true,
433 /*FIXME: CPUID leaf 0x80000005 is inconsistent with leaves 2 & 4 */
434 static CPUCacheInfo legacy_l1d_cache_amd = {
435 .type = DATA_CACHE,
436 .level = 1,
437 .size = 64 * KiB,
438 .self_init = 1,
439 .line_size = 64,
440 .associativity = 2,
441 .sets = 512,
442 .partitions = 1,
443 .lines_per_tag = 1,
444 .no_invd_sharing = true,
447 /* L1 instruction cache: */
448 static CPUCacheInfo legacy_l1i_cache = {
449 .type = INSTRUCTION_CACHE,
450 .level = 1,
451 .size = 32 * KiB,
452 .self_init = 1,
453 .line_size = 64,
454 .associativity = 8,
455 .sets = 64,
456 .partitions = 1,
457 .no_invd_sharing = true,
460 /*FIXME: CPUID leaf 0x80000005 is inconsistent with leaves 2 & 4 */
461 static CPUCacheInfo legacy_l1i_cache_amd = {
462 .type = INSTRUCTION_CACHE,
463 .level = 1,
464 .size = 64 * KiB,
465 .self_init = 1,
466 .line_size = 64,
467 .associativity = 2,
468 .sets = 512,
469 .partitions = 1,
470 .lines_per_tag = 1,
471 .no_invd_sharing = true,
474 /* Level 2 unified cache: */
475 static CPUCacheInfo legacy_l2_cache = {
476 .type = UNIFIED_CACHE,
477 .level = 2,
478 .size = 4 * MiB,
479 .self_init = 1,
480 .line_size = 64,
481 .associativity = 16,
482 .sets = 4096,
483 .partitions = 1,
484 .no_invd_sharing = true,
487 /*FIXME: CPUID leaf 2 descriptor is inconsistent with CPUID leaf 4 */
488 static CPUCacheInfo legacy_l2_cache_cpuid2 = {
489 .type = UNIFIED_CACHE,
490 .level = 2,
491 .size = 2 * MiB,
492 .line_size = 64,
493 .associativity = 8,
497 /*FIXME: CPUID leaf 0x80000006 is inconsistent with leaves 2 & 4 */
498 static CPUCacheInfo legacy_l2_cache_amd = {
499 .type = UNIFIED_CACHE,
500 .level = 2,
501 .size = 512 * KiB,
502 .line_size = 64,
503 .lines_per_tag = 1,
504 .associativity = 16,
505 .sets = 512,
506 .partitions = 1,
509 /* Level 3 unified cache: */
510 static CPUCacheInfo legacy_l3_cache = {
511 .type = UNIFIED_CACHE,
512 .level = 3,
513 .size = 16 * MiB,
514 .line_size = 64,
515 .associativity = 16,
516 .sets = 16384,
517 .partitions = 1,
518 .lines_per_tag = 1,
519 .self_init = true,
520 .inclusive = true,
521 .complex_indexing = true,
524 /* TLB definitions: */
526 #define L1_DTLB_2M_ASSOC 1
527 #define L1_DTLB_2M_ENTRIES 255
528 #define L1_DTLB_4K_ASSOC 1
529 #define L1_DTLB_4K_ENTRIES 255
531 #define L1_ITLB_2M_ASSOC 1
532 #define L1_ITLB_2M_ENTRIES 255
533 #define L1_ITLB_4K_ASSOC 1
534 #define L1_ITLB_4K_ENTRIES 255
536 #define L2_DTLB_2M_ASSOC 0 /* disabled */
537 #define L2_DTLB_2M_ENTRIES 0 /* disabled */
538 #define L2_DTLB_4K_ASSOC 4
539 #define L2_DTLB_4K_ENTRIES 512
541 #define L2_ITLB_2M_ASSOC 0 /* disabled */
542 #define L2_ITLB_2M_ENTRIES 0 /* disabled */
543 #define L2_ITLB_4K_ASSOC 4
544 #define L2_ITLB_4K_ENTRIES 512
546 /* CPUID Leaf 0x14 constants: */
547 #define INTEL_PT_MAX_SUBLEAF 0x1
549 * bit[00]: IA32_RTIT_CTL.CR3 filter can be set to 1 and IA32_RTIT_CR3_MATCH
550 * MSR can be accessed;
551 * bit[01]: Support Configurable PSB and Cycle-Accurate Mode;
552 * bit[02]: Support IP Filtering, TraceStop filtering, and preservation
553 * of Intel PT MSRs across warm reset;
554 * bit[03]: Support MTC timing packet and suppression of COFI-based packets;
556 #define INTEL_PT_MINIMAL_EBX 0xf
558 * bit[00]: Tracing can be enabled with IA32_RTIT_CTL.ToPA = 1 and
559 * IA32_RTIT_OUTPUT_BASE and IA32_RTIT_OUTPUT_MASK_PTRS MSRs can be
560 * accessed;
561 * bit[01]: ToPA tables can hold any number of output entries, up to the
562 * maximum allowed by the MaskOrTableOffset field of
563 * IA32_RTIT_OUTPUT_MASK_PTRS;
564 * bit[02]: Support Single-Range Output scheme;
566 #define INTEL_PT_MINIMAL_ECX 0x7
567 /* generated packets which contain IP payloads have LIP values */
568 #define INTEL_PT_IP_LIP (1 << 31)
569 #define INTEL_PT_ADDR_RANGES_NUM 0x2 /* Number of configurable address ranges */
570 #define INTEL_PT_ADDR_RANGES_NUM_MASK 0x3
571 #define INTEL_PT_MTC_BITMAP (0x0249 << 16) /* Support ART(0,3,6,9) */
572 #define INTEL_PT_CYCLE_BITMAP 0x1fff /* Support 0,2^(0~11) */
573 #define INTEL_PT_PSB_BITMAP (0x003f << 16) /* Support 2K,4K,8K,16K,32K,64K */
575 void x86_cpu_vendor_words2str(char *dst, uint32_t vendor1,
576 uint32_t vendor2, uint32_t vendor3)
578 int i;
579 for (i = 0; i < 4; i++) {
580 dst[i] = vendor1 >> (8 * i);
581 dst[i + 4] = vendor2 >> (8 * i);
582 dst[i + 8] = vendor3 >> (8 * i);
584 dst[CPUID_VENDOR_SZ] = '\0';
587 #define I486_FEATURES (CPUID_FP87 | CPUID_VME | CPUID_PSE)
588 #define PENTIUM_FEATURES (I486_FEATURES | CPUID_DE | CPUID_TSC | \
589 CPUID_MSR | CPUID_MCE | CPUID_CX8 | CPUID_MMX | CPUID_APIC)
590 #define PENTIUM2_FEATURES (PENTIUM_FEATURES | CPUID_PAE | CPUID_SEP | \
591 CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV | CPUID_PAT | \
592 CPUID_PSE36 | CPUID_FXSR)
593 #define PENTIUM3_FEATURES (PENTIUM2_FEATURES | CPUID_SSE)
594 #define PPRO_FEATURES (CPUID_FP87 | CPUID_DE | CPUID_PSE | CPUID_TSC | \
595 CPUID_MSR | CPUID_MCE | CPUID_CX8 | CPUID_PGE | CPUID_CMOV | \
596 CPUID_PAT | CPUID_FXSR | CPUID_MMX | CPUID_SSE | CPUID_SSE2 | \
597 CPUID_PAE | CPUID_SEP | CPUID_APIC)
599 #define TCG_FEATURES (CPUID_FP87 | CPUID_PSE | CPUID_TSC | CPUID_MSR | \
600 CPUID_PAE | CPUID_MCE | CPUID_CX8 | CPUID_APIC | CPUID_SEP | \
601 CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV | CPUID_PAT | \
602 CPUID_PSE36 | CPUID_CLFLUSH | CPUID_ACPI | CPUID_MMX | \
603 CPUID_FXSR | CPUID_SSE | CPUID_SSE2 | CPUID_SS | CPUID_DE)
604 /* partly implemented:
605 CPUID_MTRR, CPUID_MCA, CPUID_CLFLUSH (needed for Win64) */
606 /* missing:
607 CPUID_VME, CPUID_DTS, CPUID_SS, CPUID_HT, CPUID_TM, CPUID_PBE */
608 #define TCG_EXT_FEATURES (CPUID_EXT_SSE3 | CPUID_EXT_PCLMULQDQ | \
609 CPUID_EXT_MONITOR | CPUID_EXT_SSSE3 | CPUID_EXT_CX16 | \
610 CPUID_EXT_SSE41 | CPUID_EXT_SSE42 | CPUID_EXT_POPCNT | \
611 CPUID_EXT_XSAVE | /* CPUID_EXT_OSXSAVE is dynamic */ \
612 CPUID_EXT_MOVBE | CPUID_EXT_AES | CPUID_EXT_HYPERVISOR | \
613 CPUID_EXT_RDRAND)
614 /* missing:
615 CPUID_EXT_DTES64, CPUID_EXT_DSCPL, CPUID_EXT_VMX, CPUID_EXT_SMX,
616 CPUID_EXT_EST, CPUID_EXT_TM2, CPUID_EXT_CID, CPUID_EXT_FMA,
617 CPUID_EXT_XTPR, CPUID_EXT_PDCM, CPUID_EXT_PCID, CPUID_EXT_DCA,
618 CPUID_EXT_X2APIC, CPUID_EXT_TSC_DEADLINE_TIMER, CPUID_EXT_AVX,
619 CPUID_EXT_F16C */
621 #ifdef TARGET_X86_64
622 #define TCG_EXT2_X86_64_FEATURES (CPUID_EXT2_SYSCALL | CPUID_EXT2_LM)
623 #else
624 #define TCG_EXT2_X86_64_FEATURES 0
625 #endif
627 #define TCG_EXT2_FEATURES ((TCG_FEATURES & CPUID_EXT2_AMD_ALIASES) | \
628 CPUID_EXT2_NX | CPUID_EXT2_MMXEXT | CPUID_EXT2_RDTSCP | \
629 CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT | CPUID_EXT2_PDPE1GB | \
630 TCG_EXT2_X86_64_FEATURES)
631 #define TCG_EXT3_FEATURES (CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM | \
632 CPUID_EXT3_CR8LEG | CPUID_EXT3_ABM | CPUID_EXT3_SSE4A)
633 #define TCG_EXT4_FEATURES 0
634 #define TCG_SVM_FEATURES (CPUID_SVM_NPT | CPUID_SVM_VGIF | \
635 CPUID_SVM_SVME_ADDR_CHK)
636 #define TCG_KVM_FEATURES 0
637 #define TCG_7_0_EBX_FEATURES (CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_SMAP | \
638 CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ADX | \
639 CPUID_7_0_EBX_PCOMMIT | CPUID_7_0_EBX_CLFLUSHOPT | \
640 CPUID_7_0_EBX_CLWB | CPUID_7_0_EBX_MPX | CPUID_7_0_EBX_FSGSBASE | \
641 CPUID_7_0_EBX_ERMS)
642 /* missing:
643 CPUID_7_0_EBX_HLE, CPUID_7_0_EBX_AVX2,
644 CPUID_7_0_EBX_INVPCID, CPUID_7_0_EBX_RTM,
645 CPUID_7_0_EBX_RDSEED */
646 #define TCG_7_0_ECX_FEATURES (CPUID_7_0_ECX_PKU | \
647 /* CPUID_7_0_ECX_OSPKE is dynamic */ \
648 CPUID_7_0_ECX_LA57 | CPUID_7_0_ECX_PKS)
649 #define TCG_7_0_EDX_FEATURES 0
650 #define TCG_7_1_EAX_FEATURES 0
651 #define TCG_APM_FEATURES 0
652 #define TCG_6_EAX_FEATURES CPUID_6_EAX_ARAT
653 #define TCG_XSAVE_FEATURES (CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XGETBV1)
654 /* missing:
655 CPUID_XSAVE_XSAVEC, CPUID_XSAVE_XSAVES */
656 #define TCG_14_0_ECX_FEATURES 0
658 FeatureWordInfo feature_word_info[FEATURE_WORDS] = {
659 [FEAT_1_EDX] = {
660 .type = CPUID_FEATURE_WORD,
661 .feat_names = {
662 "fpu", "vme", "de", "pse",
663 "tsc", "msr", "pae", "mce",
664 "cx8", "apic", NULL, "sep",
665 "mtrr", "pge", "mca", "cmov",
666 "pat", "pse36", "pn" /* Intel psn */, "clflush" /* Intel clfsh */,
667 NULL, "ds" /* Intel dts */, "acpi", "mmx",
668 "fxsr", "sse", "sse2", "ss",
669 "ht" /* Intel htt */, "tm", "ia64", "pbe",
671 .cpuid = {.eax = 1, .reg = R_EDX, },
672 .tcg_features = TCG_FEATURES,
674 [FEAT_1_ECX] = {
675 .type = CPUID_FEATURE_WORD,
676 .feat_names = {
677 "pni" /* Intel,AMD sse3 */, "pclmulqdq", "dtes64", "monitor",
678 "ds-cpl", "vmx", "smx", "est",
679 "tm2", "ssse3", "cid", NULL,
680 "fma", "cx16", "xtpr", "pdcm",
681 NULL, "pcid", "dca", "sse4.1",
682 "sse4.2", "x2apic", "movbe", "popcnt",
683 "tsc-deadline", "aes", "xsave", NULL /* osxsave */,
684 "avx", "f16c", "rdrand", "hypervisor",
686 .cpuid = { .eax = 1, .reg = R_ECX, },
687 .tcg_features = TCG_EXT_FEATURES,
689 /* Feature names that are already defined on feature_name[] but
690 * are set on CPUID[8000_0001].EDX on AMD CPUs don't have their
691 * names on feat_names below. They are copied automatically
692 * to features[FEAT_8000_0001_EDX] if and only if CPU vendor is AMD.
694 [FEAT_8000_0001_EDX] = {
695 .type = CPUID_FEATURE_WORD,
696 .feat_names = {
697 NULL /* fpu */, NULL /* vme */, NULL /* de */, NULL /* pse */,
698 NULL /* tsc */, NULL /* msr */, NULL /* pae */, NULL /* mce */,
699 NULL /* cx8 */, NULL /* apic */, NULL, "syscall",
700 NULL /* mtrr */, NULL /* pge */, NULL /* mca */, NULL /* cmov */,
701 NULL /* pat */, NULL /* pse36 */, NULL, NULL /* Linux mp */,
702 "nx", NULL, "mmxext", NULL /* mmx */,
703 NULL /* fxsr */, "fxsr-opt", "pdpe1gb", "rdtscp",
704 NULL, "lm", "3dnowext", "3dnow",
706 .cpuid = { .eax = 0x80000001, .reg = R_EDX, },
707 .tcg_features = TCG_EXT2_FEATURES,
709 [FEAT_8000_0001_ECX] = {
710 .type = CPUID_FEATURE_WORD,
711 .feat_names = {
712 "lahf-lm", "cmp-legacy", "svm", "extapic",
713 "cr8legacy", "abm", "sse4a", "misalignsse",
714 "3dnowprefetch", "osvw", "ibs", "xop",
715 "skinit", "wdt", NULL, "lwp",
716 "fma4", "tce", NULL, "nodeid-msr",
717 NULL, "tbm", "topoext", "perfctr-core",
718 "perfctr-nb", NULL, NULL, NULL,
719 NULL, NULL, NULL, NULL,
721 .cpuid = { .eax = 0x80000001, .reg = R_ECX, },
722 .tcg_features = TCG_EXT3_FEATURES,
724 * TOPOEXT is always allowed but can't be enabled blindly by
725 * "-cpu host", as it requires consistent cache topology info
726 * to be provided so it doesn't confuse guests.
728 .no_autoenable_flags = CPUID_EXT3_TOPOEXT,
730 [FEAT_C000_0001_EDX] = {
731 .type = CPUID_FEATURE_WORD,
732 .feat_names = {
733 NULL, NULL, "xstore", "xstore-en",
734 NULL, NULL, "xcrypt", "xcrypt-en",
735 "ace2", "ace2-en", "phe", "phe-en",
736 "pmm", "pmm-en", NULL, NULL,
737 NULL, NULL, NULL, NULL,
738 NULL, NULL, NULL, NULL,
739 NULL, NULL, NULL, NULL,
740 NULL, NULL, NULL, NULL,
742 .cpuid = { .eax = 0xC0000001, .reg = R_EDX, },
743 .tcg_features = TCG_EXT4_FEATURES,
745 [FEAT_KVM] = {
746 .type = CPUID_FEATURE_WORD,
747 .feat_names = {
748 "kvmclock", "kvm-nopiodelay", "kvm-mmu", "kvmclock",
749 "kvm-asyncpf", "kvm-steal-time", "kvm-pv-eoi", "kvm-pv-unhalt",
750 NULL, "kvm-pv-tlb-flush", NULL, "kvm-pv-ipi",
751 "kvm-poll-control", "kvm-pv-sched-yield", "kvm-asyncpf-int", "kvm-msi-ext-dest-id",
752 NULL, NULL, NULL, NULL,
753 NULL, NULL, NULL, NULL,
754 "kvmclock-stable-bit", NULL, NULL, NULL,
755 NULL, NULL, NULL, NULL,
757 .cpuid = { .eax = KVM_CPUID_FEATURES, .reg = R_EAX, },
758 .tcg_features = TCG_KVM_FEATURES,
760 [FEAT_KVM_HINTS] = {
761 .type = CPUID_FEATURE_WORD,
762 .feat_names = {
763 "kvm-hint-dedicated", NULL, NULL, NULL,
764 NULL, NULL, NULL, NULL,
765 NULL, NULL, NULL, NULL,
766 NULL, NULL, NULL, NULL,
767 NULL, NULL, NULL, NULL,
768 NULL, NULL, NULL, NULL,
769 NULL, NULL, NULL, NULL,
770 NULL, NULL, NULL, NULL,
772 .cpuid = { .eax = KVM_CPUID_FEATURES, .reg = R_EDX, },
773 .tcg_features = TCG_KVM_FEATURES,
775 * KVM hints aren't auto-enabled by -cpu host, they need to be
776 * explicitly enabled in the command-line.
778 .no_autoenable_flags = ~0U,
780 [FEAT_SVM] = {
781 .type = CPUID_FEATURE_WORD,
782 .feat_names = {
783 "npt", "lbrv", "svm-lock", "nrip-save",
784 "tsc-scale", "vmcb-clean", "flushbyasid", "decodeassists",
785 NULL, NULL, "pause-filter", NULL,
786 "pfthreshold", "avic", NULL, "v-vmsave-vmload",
787 "vgif", NULL, NULL, NULL,
788 NULL, NULL, NULL, NULL,
789 NULL, NULL, NULL, NULL,
790 "svme-addr-chk", NULL, NULL, NULL,
792 .cpuid = { .eax = 0x8000000A, .reg = R_EDX, },
793 .tcg_features = TCG_SVM_FEATURES,
795 [FEAT_7_0_EBX] = {
796 .type = CPUID_FEATURE_WORD,
797 .feat_names = {
798 "fsgsbase", "tsc-adjust", NULL, "bmi1",
799 "hle", "avx2", NULL, "smep",
800 "bmi2", "erms", "invpcid", "rtm",
801 NULL, NULL, "mpx", NULL,
802 "avx512f", "avx512dq", "rdseed", "adx",
803 "smap", "avx512ifma", "pcommit", "clflushopt",
804 "clwb", "intel-pt", "avx512pf", "avx512er",
805 "avx512cd", "sha-ni", "avx512bw", "avx512vl",
807 .cpuid = {
808 .eax = 7,
809 .needs_ecx = true, .ecx = 0,
810 .reg = R_EBX,
812 .tcg_features = TCG_7_0_EBX_FEATURES,
814 [FEAT_7_0_ECX] = {
815 .type = CPUID_FEATURE_WORD,
816 .feat_names = {
817 NULL, "avx512vbmi", "umip", "pku",
818 NULL /* ospke */, "waitpkg", "avx512vbmi2", NULL,
819 "gfni", "vaes", "vpclmulqdq", "avx512vnni",
820 "avx512bitalg", NULL, "avx512-vpopcntdq", NULL,
821 "la57", NULL, NULL, NULL,
822 NULL, NULL, "rdpid", NULL,
823 "bus-lock-detect", "cldemote", NULL, "movdiri",
824 "movdir64b", NULL, NULL, "pks",
826 .cpuid = {
827 .eax = 7,
828 .needs_ecx = true, .ecx = 0,
829 .reg = R_ECX,
831 .tcg_features = TCG_7_0_ECX_FEATURES,
833 [FEAT_7_0_EDX] = {
834 .type = CPUID_FEATURE_WORD,
835 .feat_names = {
836 NULL, NULL, "avx512-4vnniw", "avx512-4fmaps",
837 "fsrm", NULL, NULL, NULL,
838 "avx512-vp2intersect", NULL, "md-clear", NULL,
839 NULL, NULL, "serialize", NULL,
840 "tsx-ldtrk", NULL, NULL /* pconfig */, NULL,
841 NULL, NULL, NULL, "avx512-fp16",
842 NULL, NULL, "spec-ctrl", "stibp",
843 NULL, "arch-capabilities", "core-capability", "ssbd",
845 .cpuid = {
846 .eax = 7,
847 .needs_ecx = true, .ecx = 0,
848 .reg = R_EDX,
850 .tcg_features = TCG_7_0_EDX_FEATURES,
852 [FEAT_7_1_EAX] = {
853 .type = CPUID_FEATURE_WORD,
854 .feat_names = {
855 NULL, NULL, NULL, NULL,
856 "avx-vnni", "avx512-bf16", NULL, NULL,
857 NULL, NULL, NULL, NULL,
858 NULL, NULL, NULL, NULL,
859 NULL, NULL, NULL, NULL,
860 NULL, NULL, NULL, NULL,
861 NULL, NULL, NULL, NULL,
862 NULL, NULL, NULL, NULL,
864 .cpuid = {
865 .eax = 7,
866 .needs_ecx = true, .ecx = 1,
867 .reg = R_EAX,
869 .tcg_features = TCG_7_1_EAX_FEATURES,
871 [FEAT_8000_0007_EDX] = {
872 .type = CPUID_FEATURE_WORD,
873 .feat_names = {
874 NULL, NULL, NULL, NULL,
875 NULL, NULL, NULL, NULL,
876 "invtsc", NULL, NULL, NULL,
877 NULL, NULL, NULL, NULL,
878 NULL, NULL, NULL, NULL,
879 NULL, NULL, NULL, NULL,
880 NULL, NULL, NULL, NULL,
881 NULL, NULL, NULL, NULL,
883 .cpuid = { .eax = 0x80000007, .reg = R_EDX, },
884 .tcg_features = TCG_APM_FEATURES,
885 .unmigratable_flags = CPUID_APM_INVTSC,
887 [FEAT_8000_0008_EBX] = {
888 .type = CPUID_FEATURE_WORD,
889 .feat_names = {
890 "clzero", NULL, "xsaveerptr", NULL,
891 NULL, NULL, NULL, NULL,
892 NULL, "wbnoinvd", NULL, NULL,
893 "ibpb", NULL, "ibrs", "amd-stibp",
894 NULL, NULL, NULL, NULL,
895 NULL, NULL, NULL, NULL,
896 "amd-ssbd", "virt-ssbd", "amd-no-ssb", NULL,
897 NULL, NULL, NULL, NULL,
899 .cpuid = { .eax = 0x80000008, .reg = R_EBX, },
900 .tcg_features = 0,
901 .unmigratable_flags = 0,
903 [FEAT_XSAVE] = {
904 .type = CPUID_FEATURE_WORD,
905 .feat_names = {
906 "xsaveopt", "xsavec", "xgetbv1", "xsaves",
907 NULL, NULL, NULL, NULL,
908 NULL, NULL, NULL, NULL,
909 NULL, NULL, NULL, NULL,
910 NULL, NULL, NULL, NULL,
911 NULL, NULL, NULL, NULL,
912 NULL, NULL, NULL, NULL,
913 NULL, NULL, NULL, NULL,
915 .cpuid = {
916 .eax = 0xd,
917 .needs_ecx = true, .ecx = 1,
918 .reg = R_EAX,
920 .tcg_features = TCG_XSAVE_FEATURES,
922 [FEAT_6_EAX] = {
923 .type = CPUID_FEATURE_WORD,
924 .feat_names = {
925 NULL, NULL, "arat", NULL,
926 NULL, NULL, NULL, NULL,
927 NULL, NULL, NULL, NULL,
928 NULL, NULL, NULL, NULL,
929 NULL, NULL, NULL, NULL,
930 NULL, NULL, NULL, NULL,
931 NULL, NULL, NULL, NULL,
932 NULL, NULL, NULL, NULL,
934 .cpuid = { .eax = 6, .reg = R_EAX, },
935 .tcg_features = TCG_6_EAX_FEATURES,
937 [FEAT_XSAVE_COMP_LO] = {
938 .type = CPUID_FEATURE_WORD,
939 .cpuid = {
940 .eax = 0xD,
941 .needs_ecx = true, .ecx = 0,
942 .reg = R_EAX,
944 .tcg_features = ~0U,
945 .migratable_flags = XSTATE_FP_MASK | XSTATE_SSE_MASK |
946 XSTATE_YMM_MASK | XSTATE_BNDREGS_MASK | XSTATE_BNDCSR_MASK |
947 XSTATE_OPMASK_MASK | XSTATE_ZMM_Hi256_MASK | XSTATE_Hi16_ZMM_MASK |
948 XSTATE_PKRU_MASK,
950 [FEAT_XSAVE_COMP_HI] = {
951 .type = CPUID_FEATURE_WORD,
952 .cpuid = {
953 .eax = 0xD,
954 .needs_ecx = true, .ecx = 0,
955 .reg = R_EDX,
957 .tcg_features = ~0U,
959 /*Below are MSR exposed features*/
960 [FEAT_ARCH_CAPABILITIES] = {
961 .type = MSR_FEATURE_WORD,
962 .feat_names = {
963 "rdctl-no", "ibrs-all", "rsba", "skip-l1dfl-vmentry",
964 "ssb-no", "mds-no", "pschange-mc-no", "tsx-ctrl",
965 "taa-no", NULL, NULL, NULL,
966 NULL, NULL, NULL, NULL,
967 NULL, NULL, NULL, NULL,
968 NULL, NULL, NULL, NULL,
969 NULL, NULL, NULL, NULL,
970 NULL, NULL, NULL, NULL,
972 .msr = {
973 .index = MSR_IA32_ARCH_CAPABILITIES,
976 [FEAT_CORE_CAPABILITY] = {
977 .type = MSR_FEATURE_WORD,
978 .feat_names = {
979 NULL, NULL, NULL, NULL,
980 NULL, "split-lock-detect", NULL, NULL,
981 NULL, NULL, NULL, NULL,
982 NULL, NULL, NULL, NULL,
983 NULL, NULL, NULL, NULL,
984 NULL, NULL, NULL, NULL,
985 NULL, NULL, NULL, NULL,
986 NULL, NULL, NULL, NULL,
988 .msr = {
989 .index = MSR_IA32_CORE_CAPABILITY,
992 [FEAT_PERF_CAPABILITIES] = {
993 .type = MSR_FEATURE_WORD,
994 .feat_names = {
995 NULL, NULL, NULL, NULL,
996 NULL, NULL, NULL, NULL,
997 NULL, NULL, NULL, NULL,
998 NULL, "full-width-write", NULL, NULL,
999 NULL, NULL, NULL, NULL,
1000 NULL, NULL, NULL, NULL,
1001 NULL, NULL, NULL, NULL,
1002 NULL, NULL, NULL, NULL,
1004 .msr = {
1005 .index = MSR_IA32_PERF_CAPABILITIES,
1009 [FEAT_VMX_PROCBASED_CTLS] = {
1010 .type = MSR_FEATURE_WORD,
1011 .feat_names = {
1012 NULL, NULL, "vmx-vintr-pending", "vmx-tsc-offset",
1013 NULL, NULL, NULL, "vmx-hlt-exit",
1014 NULL, "vmx-invlpg-exit", "vmx-mwait-exit", "vmx-rdpmc-exit",
1015 "vmx-rdtsc-exit", NULL, NULL, "vmx-cr3-load-noexit",
1016 "vmx-cr3-store-noexit", NULL, NULL, "vmx-cr8-load-exit",
1017 "vmx-cr8-store-exit", "vmx-flexpriority", "vmx-vnmi-pending", "vmx-movdr-exit",
1018 "vmx-io-exit", "vmx-io-bitmap", NULL, "vmx-mtf",
1019 "vmx-msr-bitmap", "vmx-monitor-exit", "vmx-pause-exit", "vmx-secondary-ctls",
1021 .msr = {
1022 .index = MSR_IA32_VMX_TRUE_PROCBASED_CTLS,
1026 [FEAT_VMX_SECONDARY_CTLS] = {
1027 .type = MSR_FEATURE_WORD,
1028 .feat_names = {
1029 "vmx-apicv-xapic", "vmx-ept", "vmx-desc-exit", "vmx-rdtscp-exit",
1030 "vmx-apicv-x2apic", "vmx-vpid", "vmx-wbinvd-exit", "vmx-unrestricted-guest",
1031 "vmx-apicv-register", "vmx-apicv-vid", "vmx-ple", "vmx-rdrand-exit",
1032 "vmx-invpcid-exit", "vmx-vmfunc", "vmx-shadow-vmcs", "vmx-encls-exit",
1033 "vmx-rdseed-exit", "vmx-pml", NULL, NULL,
1034 "vmx-xsaves", NULL, NULL, NULL,
1035 NULL, "vmx-tsc-scaling", NULL, NULL,
1036 NULL, NULL, NULL, NULL,
1038 .msr = {
1039 .index = MSR_IA32_VMX_PROCBASED_CTLS2,
1043 [FEAT_VMX_PINBASED_CTLS] = {
1044 .type = MSR_FEATURE_WORD,
1045 .feat_names = {
1046 "vmx-intr-exit", NULL, NULL, "vmx-nmi-exit",
1047 NULL, "vmx-vnmi", "vmx-preemption-timer", "vmx-posted-intr",
1048 NULL, NULL, NULL, NULL,
1049 NULL, NULL, NULL, NULL,
1050 NULL, NULL, NULL, NULL,
1051 NULL, NULL, NULL, NULL,
1052 NULL, NULL, NULL, NULL,
1053 NULL, NULL, NULL, NULL,
1055 .msr = {
1056 .index = MSR_IA32_VMX_TRUE_PINBASED_CTLS,
1060 [FEAT_VMX_EXIT_CTLS] = {
1061 .type = MSR_FEATURE_WORD,
1063 * VMX_VM_EXIT_HOST_ADDR_SPACE_SIZE is copied from
1064 * the LM CPUID bit.
1066 .feat_names = {
1067 NULL, NULL, "vmx-exit-nosave-debugctl", NULL,
1068 NULL, NULL, NULL, NULL,
1069 NULL, NULL /* vmx-exit-host-addr-space-size */, NULL, NULL,
1070 "vmx-exit-load-perf-global-ctrl", NULL, NULL, "vmx-exit-ack-intr",
1071 NULL, NULL, "vmx-exit-save-pat", "vmx-exit-load-pat",
1072 "vmx-exit-save-efer", "vmx-exit-load-efer",
1073 "vmx-exit-save-preemption-timer", "vmx-exit-clear-bndcfgs",
1074 NULL, "vmx-exit-clear-rtit-ctl", NULL, NULL,
1075 NULL, "vmx-exit-load-pkrs", NULL, NULL,
1077 .msr = {
1078 .index = MSR_IA32_VMX_TRUE_EXIT_CTLS,
1082 [FEAT_VMX_ENTRY_CTLS] = {
1083 .type = MSR_FEATURE_WORD,
1084 .feat_names = {
1085 NULL, NULL, "vmx-entry-noload-debugctl", NULL,
1086 NULL, NULL, NULL, NULL,
1087 NULL, "vmx-entry-ia32e-mode", NULL, NULL,
1088 NULL, "vmx-entry-load-perf-global-ctrl", "vmx-entry-load-pat", "vmx-entry-load-efer",
1089 "vmx-entry-load-bndcfgs", NULL, "vmx-entry-load-rtit-ctl", NULL,
1090 NULL, NULL, "vmx-entry-load-pkrs", NULL,
1091 NULL, NULL, NULL, NULL,
1092 NULL, NULL, NULL, NULL,
1094 .msr = {
1095 .index = MSR_IA32_VMX_TRUE_ENTRY_CTLS,
1099 [FEAT_VMX_MISC] = {
1100 .type = MSR_FEATURE_WORD,
1101 .feat_names = {
1102 NULL, NULL, NULL, NULL,
1103 NULL, "vmx-store-lma", "vmx-activity-hlt", "vmx-activity-shutdown",
1104 "vmx-activity-wait-sipi", NULL, NULL, NULL,
1105 NULL, NULL, NULL, NULL,
1106 NULL, NULL, NULL, NULL,
1107 NULL, NULL, NULL, NULL,
1108 NULL, NULL, NULL, NULL,
1109 NULL, "vmx-vmwrite-vmexit-fields", "vmx-zero-len-inject", NULL,
1111 .msr = {
1112 .index = MSR_IA32_VMX_MISC,
1116 [FEAT_VMX_EPT_VPID_CAPS] = {
1117 .type = MSR_FEATURE_WORD,
1118 .feat_names = {
1119 "vmx-ept-execonly", NULL, NULL, NULL,
1120 NULL, NULL, "vmx-page-walk-4", "vmx-page-walk-5",
1121 NULL, NULL, NULL, NULL,
1122 NULL, NULL, NULL, NULL,
1123 "vmx-ept-2mb", "vmx-ept-1gb", NULL, NULL,
1124 "vmx-invept", "vmx-eptad", "vmx-ept-advanced-exitinfo", NULL,
1125 NULL, "vmx-invept-single-context", "vmx-invept-all-context", NULL,
1126 NULL, NULL, NULL, NULL,
1127 "vmx-invvpid", NULL, NULL, NULL,
1128 NULL, NULL, NULL, NULL,
1129 "vmx-invvpid-single-addr", "vmx-invept-single-context",
1130 "vmx-invvpid-all-context", "vmx-invept-single-context-noglobals",
1131 NULL, NULL, NULL, NULL,
1132 NULL, NULL, NULL, NULL,
1133 NULL, NULL, NULL, NULL,
1134 NULL, NULL, NULL, NULL,
1135 NULL, NULL, NULL, NULL,
1137 .msr = {
1138 .index = MSR_IA32_VMX_EPT_VPID_CAP,
1142 [FEAT_VMX_BASIC] = {
1143 .type = MSR_FEATURE_WORD,
1144 .feat_names = {
1145 [54] = "vmx-ins-outs",
1146 [55] = "vmx-true-ctls",
1148 .msr = {
1149 .index = MSR_IA32_VMX_BASIC,
1151 /* Just to be safe - we don't support setting the MSEG version field. */
1152 .no_autoenable_flags = MSR_VMX_BASIC_DUAL_MONITOR,
1155 [FEAT_VMX_VMFUNC] = {
1156 .type = MSR_FEATURE_WORD,
1157 .feat_names = {
1158 [0] = "vmx-eptp-switching",
1160 .msr = {
1161 .index = MSR_IA32_VMX_VMFUNC,
1165 [FEAT_14_0_ECX] = {
1166 .type = CPUID_FEATURE_WORD,
1167 .feat_names = {
1168 NULL, NULL, NULL, NULL,
1169 NULL, NULL, NULL, NULL,
1170 NULL, NULL, NULL, NULL,
1171 NULL, NULL, NULL, NULL,
1172 NULL, NULL, NULL, NULL,
1173 NULL, NULL, NULL, NULL,
1174 NULL, NULL, NULL, NULL,
1175 NULL, NULL, NULL, "intel-pt-lip",
1177 .cpuid = {
1178 .eax = 0x14,
1179 .needs_ecx = true, .ecx = 0,
1180 .reg = R_ECX,
1182 .tcg_features = TCG_14_0_ECX_FEATURES,
1187 typedef struct FeatureMask {
1188 FeatureWord index;
1189 uint64_t mask;
1190 } FeatureMask;
1192 typedef struct FeatureDep {
1193 FeatureMask from, to;
1194 } FeatureDep;
1196 static FeatureDep feature_dependencies[] = {
1198 .from = { FEAT_7_0_EDX, CPUID_7_0_EDX_ARCH_CAPABILITIES },
1199 .to = { FEAT_ARCH_CAPABILITIES, ~0ull },
1202 .from = { FEAT_7_0_EDX, CPUID_7_0_EDX_CORE_CAPABILITY },
1203 .to = { FEAT_CORE_CAPABILITY, ~0ull },
1206 .from = { FEAT_1_ECX, CPUID_EXT_PDCM },
1207 .to = { FEAT_PERF_CAPABILITIES, ~0ull },
1210 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1211 .to = { FEAT_VMX_PROCBASED_CTLS, ~0ull },
1214 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1215 .to = { FEAT_VMX_PINBASED_CTLS, ~0ull },
1218 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1219 .to = { FEAT_VMX_EXIT_CTLS, ~0ull },
1222 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1223 .to = { FEAT_VMX_ENTRY_CTLS, ~0ull },
1226 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1227 .to = { FEAT_VMX_MISC, ~0ull },
1230 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1231 .to = { FEAT_VMX_BASIC, ~0ull },
1234 .from = { FEAT_8000_0001_EDX, CPUID_EXT2_LM },
1235 .to = { FEAT_VMX_ENTRY_CTLS, VMX_VM_ENTRY_IA32E_MODE },
1238 .from = { FEAT_VMX_PROCBASED_CTLS, VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS },
1239 .to = { FEAT_VMX_SECONDARY_CTLS, ~0ull },
1242 .from = { FEAT_XSAVE, CPUID_XSAVE_XSAVES },
1243 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_XSAVES },
1246 .from = { FEAT_1_ECX, CPUID_EXT_RDRAND },
1247 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_RDRAND_EXITING },
1250 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_INVPCID },
1251 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_INVPCID },
1254 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_RDSEED },
1255 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_RDSEED_EXITING },
1258 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_INTEL_PT },
1259 .to = { FEAT_14_0_ECX, ~0ull },
1262 .from = { FEAT_8000_0001_EDX, CPUID_EXT2_RDTSCP },
1263 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_RDTSCP },
1266 .from = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_EPT },
1267 .to = { FEAT_VMX_EPT_VPID_CAPS, 0xffffffffull },
1270 .from = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_EPT },
1271 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST },
1274 .from = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_VPID },
1275 .to = { FEAT_VMX_EPT_VPID_CAPS, 0xffffffffull << 32 },
1278 .from = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_VMFUNC },
1279 .to = { FEAT_VMX_VMFUNC, ~0ull },
1282 .from = { FEAT_8000_0001_ECX, CPUID_EXT3_SVM },
1283 .to = { FEAT_SVM, ~0ull },
1287 typedef struct X86RegisterInfo32 {
1288 /* Name of register */
1289 const char *name;
1290 /* QAPI enum value register */
1291 X86CPURegister32 qapi_enum;
1292 } X86RegisterInfo32;
1294 #define REGISTER(reg) \
1295 [R_##reg] = { .name = #reg, .qapi_enum = X86_CPU_REGISTER32_##reg }
1296 static const X86RegisterInfo32 x86_reg_info_32[CPU_NB_REGS32] = {
1297 REGISTER(EAX),
1298 REGISTER(ECX),
1299 REGISTER(EDX),
1300 REGISTER(EBX),
1301 REGISTER(ESP),
1302 REGISTER(EBP),
1303 REGISTER(ESI),
1304 REGISTER(EDI),
1306 #undef REGISTER
1308 ExtSaveArea x86_ext_save_areas[XSAVE_STATE_AREA_COUNT] = {
1309 [XSTATE_FP_BIT] = {
1310 /* x87 FP state component is always enabled if XSAVE is supported */
1311 .feature = FEAT_1_ECX, .bits = CPUID_EXT_XSAVE,
1312 .size = sizeof(X86LegacyXSaveArea) + sizeof(X86XSaveHeader),
1314 [XSTATE_SSE_BIT] = {
1315 /* SSE state component is always enabled if XSAVE is supported */
1316 .feature = FEAT_1_ECX, .bits = CPUID_EXT_XSAVE,
1317 .size = sizeof(X86LegacyXSaveArea) + sizeof(X86XSaveHeader),
1319 [XSTATE_YMM_BIT] =
1320 { .feature = FEAT_1_ECX, .bits = CPUID_EXT_AVX,
1321 .size = sizeof(XSaveAVX) },
1322 [XSTATE_BNDREGS_BIT] =
1323 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_MPX,
1324 .size = sizeof(XSaveBNDREG) },
1325 [XSTATE_BNDCSR_BIT] =
1326 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_MPX,
1327 .size = sizeof(XSaveBNDCSR) },
1328 [XSTATE_OPMASK_BIT] =
1329 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_AVX512F,
1330 .size = sizeof(XSaveOpmask) },
1331 [XSTATE_ZMM_Hi256_BIT] =
1332 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_AVX512F,
1333 .size = sizeof(XSaveZMM_Hi256) },
1334 [XSTATE_Hi16_ZMM_BIT] =
1335 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_AVX512F,
1336 .size = sizeof(XSaveHi16_ZMM) },
1337 [XSTATE_PKRU_BIT] =
1338 { .feature = FEAT_7_0_ECX, .bits = CPUID_7_0_ECX_PKU,
1339 .size = sizeof(XSavePKRU) },
1342 static uint32_t xsave_area_size(uint64_t mask)
1344 int i;
1345 uint64_t ret = 0;
1347 for (i = 0; i < ARRAY_SIZE(x86_ext_save_areas); i++) {
1348 const ExtSaveArea *esa = &x86_ext_save_areas[i];
1349 if ((mask >> i) & 1) {
1350 ret = MAX(ret, esa->offset + esa->size);
1353 return ret;
1356 static inline bool accel_uses_host_cpuid(void)
1358 return kvm_enabled() || hvf_enabled();
1361 static inline uint64_t x86_cpu_xsave_components(X86CPU *cpu)
1363 return ((uint64_t)cpu->env.features[FEAT_XSAVE_COMP_HI]) << 32 |
1364 cpu->env.features[FEAT_XSAVE_COMP_LO];
1367 /* Return name of 32-bit register, from a R_* constant */
1368 static const char *get_register_name_32(unsigned int reg)
1370 if (reg >= CPU_NB_REGS32) {
1371 return NULL;
1373 return x86_reg_info_32[reg].name;
1377 * Returns the set of feature flags that are supported and migratable by
1378 * QEMU, for a given FeatureWord.
1380 static uint64_t x86_cpu_get_migratable_flags(FeatureWord w)
1382 FeatureWordInfo *wi = &feature_word_info[w];
1383 uint64_t r = 0;
1384 int i;
1386 for (i = 0; i < 64; i++) {
1387 uint64_t f = 1ULL << i;
1389 /* If the feature name is known, it is implicitly considered migratable,
1390 * unless it is explicitly set in unmigratable_flags */
1391 if ((wi->migratable_flags & f) ||
1392 (wi->feat_names[i] && !(wi->unmigratable_flags & f))) {
1393 r |= f;
1396 return r;
1399 void host_cpuid(uint32_t function, uint32_t count,
1400 uint32_t *eax, uint32_t *ebx, uint32_t *ecx, uint32_t *edx)
1402 uint32_t vec[4];
1404 #ifdef __x86_64__
1405 asm volatile("cpuid"
1406 : "=a"(vec[0]), "=b"(vec[1]),
1407 "=c"(vec[2]), "=d"(vec[3])
1408 : "0"(function), "c"(count) : "cc");
1409 #elif defined(__i386__)
1410 asm volatile("pusha \n\t"
1411 "cpuid \n\t"
1412 "mov %%eax, 0(%2) \n\t"
1413 "mov %%ebx, 4(%2) \n\t"
1414 "mov %%ecx, 8(%2) \n\t"
1415 "mov %%edx, 12(%2) \n\t"
1416 "popa"
1417 : : "a"(function), "c"(count), "S"(vec)
1418 : "memory", "cc");
1419 #else
1420 abort();
1421 #endif
1423 if (eax)
1424 *eax = vec[0];
1425 if (ebx)
1426 *ebx = vec[1];
1427 if (ecx)
1428 *ecx = vec[2];
1429 if (edx)
1430 *edx = vec[3];
1433 /* CPU class name definitions: */
1435 /* Return type name for a given CPU model name
1436 * Caller is responsible for freeing the returned string.
1438 static char *x86_cpu_type_name(const char *model_name)
1440 return g_strdup_printf(X86_CPU_TYPE_NAME("%s"), model_name);
1443 static ObjectClass *x86_cpu_class_by_name(const char *cpu_model)
1445 g_autofree char *typename = x86_cpu_type_name(cpu_model);
1446 return object_class_by_name(typename);
1449 static char *x86_cpu_class_get_model_name(X86CPUClass *cc)
1451 const char *class_name = object_class_get_name(OBJECT_CLASS(cc));
1452 assert(g_str_has_suffix(class_name, X86_CPU_TYPE_SUFFIX));
1453 return g_strndup(class_name,
1454 strlen(class_name) - strlen(X86_CPU_TYPE_SUFFIX));
1457 typedef struct X86CPUVersionDefinition {
1458 X86CPUVersion version;
1459 const char *alias;
1460 const char *note;
1461 PropValue *props;
1462 } X86CPUVersionDefinition;
1464 /* Base definition for a CPU model */
1465 typedef struct X86CPUDefinition {
1466 const char *name;
1467 uint32_t level;
1468 uint32_t xlevel;
1469 /* vendor is zero-terminated, 12 character ASCII string */
1470 char vendor[CPUID_VENDOR_SZ + 1];
1471 int family;
1472 int model;
1473 int stepping;
1474 FeatureWordArray features;
1475 const char *model_id;
1476 const CPUCaches *const cache_info;
1478 * Definitions for alternative versions of CPU model.
1479 * List is terminated by item with version == 0.
1480 * If NULL, version 1 will be registered automatically.
1482 const X86CPUVersionDefinition *versions;
1483 const char *deprecation_note;
1484 } X86CPUDefinition;
1486 /* Reference to a specific CPU model version */
1487 struct X86CPUModel {
1488 /* Base CPU definition */
1489 const X86CPUDefinition *cpudef;
1490 /* CPU model version */
1491 X86CPUVersion version;
1492 const char *note;
1494 * If true, this is an alias CPU model.
1495 * This matters only for "-cpu help" and query-cpu-definitions
1497 bool is_alias;
1500 /* Get full model name for CPU version */
1501 static char *x86_cpu_versioned_model_name(const X86CPUDefinition *cpudef,
1502 X86CPUVersion version)
1504 assert(version > 0);
1505 return g_strdup_printf("%s-v%d", cpudef->name, (int)version);
1508 static const X86CPUVersionDefinition *
1509 x86_cpu_def_get_versions(const X86CPUDefinition *def)
1511 /* When X86CPUDefinition::versions is NULL, we register only v1 */
1512 static const X86CPUVersionDefinition default_version_list[] = {
1513 { 1 },
1514 { /* end of list */ }
1517 return def->versions ?: default_version_list;
1520 static const CPUCaches epyc_cache_info = {
1521 .l1d_cache = &(CPUCacheInfo) {
1522 .type = DATA_CACHE,
1523 .level = 1,
1524 .size = 32 * KiB,
1525 .line_size = 64,
1526 .associativity = 8,
1527 .partitions = 1,
1528 .sets = 64,
1529 .lines_per_tag = 1,
1530 .self_init = 1,
1531 .no_invd_sharing = true,
1533 .l1i_cache = &(CPUCacheInfo) {
1534 .type = INSTRUCTION_CACHE,
1535 .level = 1,
1536 .size = 64 * KiB,
1537 .line_size = 64,
1538 .associativity = 4,
1539 .partitions = 1,
1540 .sets = 256,
1541 .lines_per_tag = 1,
1542 .self_init = 1,
1543 .no_invd_sharing = true,
1545 .l2_cache = &(CPUCacheInfo) {
1546 .type = UNIFIED_CACHE,
1547 .level = 2,
1548 .size = 512 * KiB,
1549 .line_size = 64,
1550 .associativity = 8,
1551 .partitions = 1,
1552 .sets = 1024,
1553 .lines_per_tag = 1,
1555 .l3_cache = &(CPUCacheInfo) {
1556 .type = UNIFIED_CACHE,
1557 .level = 3,
1558 .size = 8 * MiB,
1559 .line_size = 64,
1560 .associativity = 16,
1561 .partitions = 1,
1562 .sets = 8192,
1563 .lines_per_tag = 1,
1564 .self_init = true,
1565 .inclusive = true,
1566 .complex_indexing = true,
1570 static const CPUCaches epyc_rome_cache_info = {
1571 .l1d_cache = &(CPUCacheInfo) {
1572 .type = DATA_CACHE,
1573 .level = 1,
1574 .size = 32 * KiB,
1575 .line_size = 64,
1576 .associativity = 8,
1577 .partitions = 1,
1578 .sets = 64,
1579 .lines_per_tag = 1,
1580 .self_init = 1,
1581 .no_invd_sharing = true,
1583 .l1i_cache = &(CPUCacheInfo) {
1584 .type = INSTRUCTION_CACHE,
1585 .level = 1,
1586 .size = 32 * KiB,
1587 .line_size = 64,
1588 .associativity = 8,
1589 .partitions = 1,
1590 .sets = 64,
1591 .lines_per_tag = 1,
1592 .self_init = 1,
1593 .no_invd_sharing = true,
1595 .l2_cache = &(CPUCacheInfo) {
1596 .type = UNIFIED_CACHE,
1597 .level = 2,
1598 .size = 512 * KiB,
1599 .line_size = 64,
1600 .associativity = 8,
1601 .partitions = 1,
1602 .sets = 1024,
1603 .lines_per_tag = 1,
1605 .l3_cache = &(CPUCacheInfo) {
1606 .type = UNIFIED_CACHE,
1607 .level = 3,
1608 .size = 16 * MiB,
1609 .line_size = 64,
1610 .associativity = 16,
1611 .partitions = 1,
1612 .sets = 16384,
1613 .lines_per_tag = 1,
1614 .self_init = true,
1615 .inclusive = true,
1616 .complex_indexing = true,
1620 static const CPUCaches epyc_milan_cache_info = {
1621 .l1d_cache = &(CPUCacheInfo) {
1622 .type = DATA_CACHE,
1623 .level = 1,
1624 .size = 32 * KiB,
1625 .line_size = 64,
1626 .associativity = 8,
1627 .partitions = 1,
1628 .sets = 64,
1629 .lines_per_tag = 1,
1630 .self_init = 1,
1631 .no_invd_sharing = true,
1633 .l1i_cache = &(CPUCacheInfo) {
1634 .type = INSTRUCTION_CACHE,
1635 .level = 1,
1636 .size = 32 * KiB,
1637 .line_size = 64,
1638 .associativity = 8,
1639 .partitions = 1,
1640 .sets = 64,
1641 .lines_per_tag = 1,
1642 .self_init = 1,
1643 .no_invd_sharing = true,
1645 .l2_cache = &(CPUCacheInfo) {
1646 .type = UNIFIED_CACHE,
1647 .level = 2,
1648 .size = 512 * KiB,
1649 .line_size = 64,
1650 .associativity = 8,
1651 .partitions = 1,
1652 .sets = 1024,
1653 .lines_per_tag = 1,
1655 .l3_cache = &(CPUCacheInfo) {
1656 .type = UNIFIED_CACHE,
1657 .level = 3,
1658 .size = 32 * MiB,
1659 .line_size = 64,
1660 .associativity = 16,
1661 .partitions = 1,
1662 .sets = 32768,
1663 .lines_per_tag = 1,
1664 .self_init = true,
1665 .inclusive = true,
1666 .complex_indexing = true,
1670 /* The following VMX features are not supported by KVM and are left out in the
1671 * CPU definitions:
1673 * Dual-monitor support (all processors)
1674 * Entry to SMM
1675 * Deactivate dual-monitor treatment
1676 * Number of CR3-target values
1677 * Shutdown activity state
1678 * Wait-for-SIPI activity state
1679 * PAUSE-loop exiting (Westmere and newer)
1680 * EPT-violation #VE (Broadwell and newer)
1681 * Inject event with insn length=0 (Skylake and newer)
1682 * Conceal non-root operation from PT
1683 * Conceal VM exits from PT
1684 * Conceal VM entries from PT
1685 * Enable ENCLS exiting
1686 * Mode-based execute control (XS/XU)
1687 s TSC scaling (Skylake Server and newer)
1688 * GPA translation for PT (IceLake and newer)
1689 * User wait and pause
1690 * ENCLV exiting
1691 * Load IA32_RTIT_CTL
1692 * Clear IA32_RTIT_CTL
1693 * Advanced VM-exit information for EPT violations
1694 * Sub-page write permissions
1695 * PT in VMX operation
1698 static const X86CPUDefinition builtin_x86_defs[] = {
1700 .name = "qemu64",
1701 .level = 0xd,
1702 .vendor = CPUID_VENDOR_AMD,
1703 .family = 15,
1704 .model = 107,
1705 .stepping = 1,
1706 .features[FEAT_1_EDX] =
1707 PPRO_FEATURES |
1708 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
1709 CPUID_PSE36,
1710 .features[FEAT_1_ECX] =
1711 CPUID_EXT_SSE3 | CPUID_EXT_CX16,
1712 .features[FEAT_8000_0001_EDX] =
1713 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
1714 .features[FEAT_8000_0001_ECX] =
1715 CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM,
1716 .xlevel = 0x8000000A,
1717 .model_id = "QEMU Virtual CPU version " QEMU_HW_VERSION,
1720 .name = "phenom",
1721 .level = 5,
1722 .vendor = CPUID_VENDOR_AMD,
1723 .family = 16,
1724 .model = 2,
1725 .stepping = 3,
1726 /* Missing: CPUID_HT */
1727 .features[FEAT_1_EDX] =
1728 PPRO_FEATURES |
1729 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
1730 CPUID_PSE36 | CPUID_VME,
1731 .features[FEAT_1_ECX] =
1732 CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_CX16 |
1733 CPUID_EXT_POPCNT,
1734 .features[FEAT_8000_0001_EDX] =
1735 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX |
1736 CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT | CPUID_EXT2_MMXEXT |
1737 CPUID_EXT2_FFXSR | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP,
1738 /* Missing: CPUID_EXT3_CMP_LEG, CPUID_EXT3_EXTAPIC,
1739 CPUID_EXT3_CR8LEG,
1740 CPUID_EXT3_MISALIGNSSE, CPUID_EXT3_3DNOWPREFETCH,
1741 CPUID_EXT3_OSVW, CPUID_EXT3_IBS */
1742 .features[FEAT_8000_0001_ECX] =
1743 CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM |
1744 CPUID_EXT3_ABM | CPUID_EXT3_SSE4A,
1745 /* Missing: CPUID_SVM_LBRV */
1746 .features[FEAT_SVM] =
1747 CPUID_SVM_NPT,
1748 .xlevel = 0x8000001A,
1749 .model_id = "AMD Phenom(tm) 9550 Quad-Core Processor"
1752 .name = "core2duo",
1753 .level = 10,
1754 .vendor = CPUID_VENDOR_INTEL,
1755 .family = 6,
1756 .model = 15,
1757 .stepping = 11,
1758 /* Missing: CPUID_DTS, CPUID_HT, CPUID_TM, CPUID_PBE */
1759 .features[FEAT_1_EDX] =
1760 PPRO_FEATURES |
1761 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
1762 CPUID_PSE36 | CPUID_VME | CPUID_ACPI | CPUID_SS,
1763 /* Missing: CPUID_EXT_DTES64, CPUID_EXT_DSCPL, CPUID_EXT_EST,
1764 * CPUID_EXT_TM2, CPUID_EXT_XTPR, CPUID_EXT_PDCM, CPUID_EXT_VMX */
1765 .features[FEAT_1_ECX] =
1766 CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_SSSE3 |
1767 CPUID_EXT_CX16,
1768 .features[FEAT_8000_0001_EDX] =
1769 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
1770 .features[FEAT_8000_0001_ECX] =
1771 CPUID_EXT3_LAHF_LM,
1772 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS,
1773 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
1774 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
1775 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
1776 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
1777 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS,
1778 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
1779 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
1780 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
1781 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
1782 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
1783 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
1784 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
1785 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
1786 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
1787 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
1788 .features[FEAT_VMX_SECONDARY_CTLS] =
1789 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES,
1790 .xlevel = 0x80000008,
1791 .model_id = "Intel(R) Core(TM)2 Duo CPU T7700 @ 2.40GHz",
1794 .name = "kvm64",
1795 .level = 0xd,
1796 .vendor = CPUID_VENDOR_INTEL,
1797 .family = 15,
1798 .model = 6,
1799 .stepping = 1,
1800 /* Missing: CPUID_HT */
1801 .features[FEAT_1_EDX] =
1802 PPRO_FEATURES | CPUID_VME |
1803 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
1804 CPUID_PSE36,
1805 /* Missing: CPUID_EXT_POPCNT, CPUID_EXT_MONITOR */
1806 .features[FEAT_1_ECX] =
1807 CPUID_EXT_SSE3 | CPUID_EXT_CX16,
1808 /* Missing: CPUID_EXT2_PDPE1GB, CPUID_EXT2_RDTSCP */
1809 .features[FEAT_8000_0001_EDX] =
1810 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
1811 /* Missing: CPUID_EXT3_LAHF_LM, CPUID_EXT3_CMP_LEG, CPUID_EXT3_EXTAPIC,
1812 CPUID_EXT3_CR8LEG, CPUID_EXT3_ABM, CPUID_EXT3_SSE4A,
1813 CPUID_EXT3_MISALIGNSSE, CPUID_EXT3_3DNOWPREFETCH,
1814 CPUID_EXT3_OSVW, CPUID_EXT3_IBS, CPUID_EXT3_SVM */
1815 .features[FEAT_8000_0001_ECX] =
1817 /* VMX features from Cedar Mill/Prescott */
1818 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
1819 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
1820 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
1821 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
1822 VMX_PIN_BASED_NMI_EXITING,
1823 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
1824 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
1825 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
1826 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
1827 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
1828 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
1829 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
1830 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING,
1831 .xlevel = 0x80000008,
1832 .model_id = "Common KVM processor"
1835 .name = "qemu32",
1836 .level = 4,
1837 .vendor = CPUID_VENDOR_INTEL,
1838 .family = 6,
1839 .model = 6,
1840 .stepping = 3,
1841 .features[FEAT_1_EDX] =
1842 PPRO_FEATURES,
1843 .features[FEAT_1_ECX] =
1844 CPUID_EXT_SSE3,
1845 .xlevel = 0x80000004,
1846 .model_id = "QEMU Virtual CPU version " QEMU_HW_VERSION,
1849 .name = "kvm32",
1850 .level = 5,
1851 .vendor = CPUID_VENDOR_INTEL,
1852 .family = 15,
1853 .model = 6,
1854 .stepping = 1,
1855 .features[FEAT_1_EDX] =
1856 PPRO_FEATURES | CPUID_VME |
1857 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_PSE36,
1858 .features[FEAT_1_ECX] =
1859 CPUID_EXT_SSE3,
1860 .features[FEAT_8000_0001_ECX] =
1862 /* VMX features from Yonah */
1863 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
1864 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
1865 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
1866 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
1867 VMX_PIN_BASED_NMI_EXITING,
1868 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
1869 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
1870 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
1871 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
1872 VMX_CPU_BASED_MOV_DR_EXITING | VMX_CPU_BASED_UNCOND_IO_EXITING |
1873 VMX_CPU_BASED_USE_IO_BITMAPS | VMX_CPU_BASED_MONITOR_EXITING |
1874 VMX_CPU_BASED_PAUSE_EXITING | VMX_CPU_BASED_USE_MSR_BITMAPS,
1875 .xlevel = 0x80000008,
1876 .model_id = "Common 32-bit KVM processor"
1879 .name = "coreduo",
1880 .level = 10,
1881 .vendor = CPUID_VENDOR_INTEL,
1882 .family = 6,
1883 .model = 14,
1884 .stepping = 8,
1885 /* Missing: CPUID_DTS, CPUID_HT, CPUID_TM, CPUID_PBE */
1886 .features[FEAT_1_EDX] =
1887 PPRO_FEATURES | CPUID_VME |
1888 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_ACPI |
1889 CPUID_SS,
1890 /* Missing: CPUID_EXT_EST, CPUID_EXT_TM2 , CPUID_EXT_XTPR,
1891 * CPUID_EXT_PDCM, CPUID_EXT_VMX */
1892 .features[FEAT_1_ECX] =
1893 CPUID_EXT_SSE3 | CPUID_EXT_MONITOR,
1894 .features[FEAT_8000_0001_EDX] =
1895 CPUID_EXT2_NX,
1896 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
1897 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
1898 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
1899 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
1900 VMX_PIN_BASED_NMI_EXITING,
1901 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
1902 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
1903 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
1904 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
1905 VMX_CPU_BASED_MOV_DR_EXITING | VMX_CPU_BASED_UNCOND_IO_EXITING |
1906 VMX_CPU_BASED_USE_IO_BITMAPS | VMX_CPU_BASED_MONITOR_EXITING |
1907 VMX_CPU_BASED_PAUSE_EXITING | VMX_CPU_BASED_USE_MSR_BITMAPS,
1908 .xlevel = 0x80000008,
1909 .model_id = "Genuine Intel(R) CPU T2600 @ 2.16GHz",
1912 .name = "486",
1913 .level = 1,
1914 .vendor = CPUID_VENDOR_INTEL,
1915 .family = 4,
1916 .model = 8,
1917 .stepping = 0,
1918 .features[FEAT_1_EDX] =
1919 I486_FEATURES,
1920 .xlevel = 0,
1921 .model_id = "",
1924 .name = "pentium",
1925 .level = 1,
1926 .vendor = CPUID_VENDOR_INTEL,
1927 .family = 5,
1928 .model = 4,
1929 .stepping = 3,
1930 .features[FEAT_1_EDX] =
1931 PENTIUM_FEATURES,
1932 .xlevel = 0,
1933 .model_id = "",
1936 .name = "pentium2",
1937 .level = 2,
1938 .vendor = CPUID_VENDOR_INTEL,
1939 .family = 6,
1940 .model = 5,
1941 .stepping = 2,
1942 .features[FEAT_1_EDX] =
1943 PENTIUM2_FEATURES,
1944 .xlevel = 0,
1945 .model_id = "",
1948 .name = "pentium3",
1949 .level = 3,
1950 .vendor = CPUID_VENDOR_INTEL,
1951 .family = 6,
1952 .model = 7,
1953 .stepping = 3,
1954 .features[FEAT_1_EDX] =
1955 PENTIUM3_FEATURES,
1956 .xlevel = 0,
1957 .model_id = "",
1960 .name = "athlon",
1961 .level = 2,
1962 .vendor = CPUID_VENDOR_AMD,
1963 .family = 6,
1964 .model = 2,
1965 .stepping = 3,
1966 .features[FEAT_1_EDX] =
1967 PPRO_FEATURES | CPUID_PSE36 | CPUID_VME | CPUID_MTRR |
1968 CPUID_MCA,
1969 .features[FEAT_8000_0001_EDX] =
1970 CPUID_EXT2_MMXEXT | CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT,
1971 .xlevel = 0x80000008,
1972 .model_id = "QEMU Virtual CPU version " QEMU_HW_VERSION,
1975 .name = "n270",
1976 .level = 10,
1977 .vendor = CPUID_VENDOR_INTEL,
1978 .family = 6,
1979 .model = 28,
1980 .stepping = 2,
1981 /* Missing: CPUID_DTS, CPUID_HT, CPUID_TM, CPUID_PBE */
1982 .features[FEAT_1_EDX] =
1983 PPRO_FEATURES |
1984 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_VME |
1985 CPUID_ACPI | CPUID_SS,
1986 /* Some CPUs got no CPUID_SEP */
1987 /* Missing: CPUID_EXT_DSCPL, CPUID_EXT_EST, CPUID_EXT_TM2,
1988 * CPUID_EXT_XTPR */
1989 .features[FEAT_1_ECX] =
1990 CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_SSSE3 |
1991 CPUID_EXT_MOVBE,
1992 .features[FEAT_8000_0001_EDX] =
1993 CPUID_EXT2_NX,
1994 .features[FEAT_8000_0001_ECX] =
1995 CPUID_EXT3_LAHF_LM,
1996 .xlevel = 0x80000008,
1997 .model_id = "Intel(R) Atom(TM) CPU N270 @ 1.60GHz",
2000 .name = "Conroe",
2001 .level = 10,
2002 .vendor = CPUID_VENDOR_INTEL,
2003 .family = 6,
2004 .model = 15,
2005 .stepping = 3,
2006 .features[FEAT_1_EDX] =
2007 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2008 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2009 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2010 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2011 CPUID_DE | CPUID_FP87,
2012 .features[FEAT_1_ECX] =
2013 CPUID_EXT_SSSE3 | CPUID_EXT_SSE3,
2014 .features[FEAT_8000_0001_EDX] =
2015 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
2016 .features[FEAT_8000_0001_ECX] =
2017 CPUID_EXT3_LAHF_LM,
2018 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS,
2019 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
2020 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
2021 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
2022 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2023 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS,
2024 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2025 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2026 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2027 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2028 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2029 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2030 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2031 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2032 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2033 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2034 .features[FEAT_VMX_SECONDARY_CTLS] =
2035 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES,
2036 .xlevel = 0x80000008,
2037 .model_id = "Intel Celeron_4x0 (Conroe/Merom Class Core 2)",
2040 .name = "Penryn",
2041 .level = 10,
2042 .vendor = CPUID_VENDOR_INTEL,
2043 .family = 6,
2044 .model = 23,
2045 .stepping = 3,
2046 .features[FEAT_1_EDX] =
2047 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2048 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2049 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2050 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2051 CPUID_DE | CPUID_FP87,
2052 .features[FEAT_1_ECX] =
2053 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2054 CPUID_EXT_SSE3,
2055 .features[FEAT_8000_0001_EDX] =
2056 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
2057 .features[FEAT_8000_0001_ECX] =
2058 CPUID_EXT3_LAHF_LM,
2059 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS,
2060 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2061 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL,
2062 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT |
2063 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL,
2064 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
2065 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2066 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS,
2067 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2068 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2069 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2070 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2071 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2072 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2073 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2074 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2075 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2076 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2077 .features[FEAT_VMX_SECONDARY_CTLS] =
2078 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2079 VMX_SECONDARY_EXEC_WBINVD_EXITING,
2080 .xlevel = 0x80000008,
2081 .model_id = "Intel Core 2 Duo P9xxx (Penryn Class Core 2)",
2084 .name = "Nehalem",
2085 .level = 11,
2086 .vendor = CPUID_VENDOR_INTEL,
2087 .family = 6,
2088 .model = 26,
2089 .stepping = 3,
2090 .features[FEAT_1_EDX] =
2091 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2092 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2093 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2094 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2095 CPUID_DE | CPUID_FP87,
2096 .features[FEAT_1_ECX] =
2097 CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
2098 CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_SSE3,
2099 .features[FEAT_8000_0001_EDX] =
2100 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
2101 .features[FEAT_8000_0001_ECX] =
2102 CPUID_EXT3_LAHF_LM,
2103 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2104 MSR_VMX_BASIC_TRUE_CTLS,
2105 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2106 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2107 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2108 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2109 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2110 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2111 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2112 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2113 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2114 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
2115 .features[FEAT_VMX_EXIT_CTLS] =
2116 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2117 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2118 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2119 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2120 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2121 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
2122 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2123 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2124 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
2125 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2126 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2127 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2128 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2129 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2130 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2131 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2132 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2133 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2134 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2135 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2136 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2137 .features[FEAT_VMX_SECONDARY_CTLS] =
2138 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2139 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2140 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2141 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2142 VMX_SECONDARY_EXEC_ENABLE_VPID,
2143 .xlevel = 0x80000008,
2144 .model_id = "Intel Core i7 9xx (Nehalem Class Core i7)",
2145 .versions = (X86CPUVersionDefinition[]) {
2146 { .version = 1 },
2148 .version = 2,
2149 .alias = "Nehalem-IBRS",
2150 .props = (PropValue[]) {
2151 { "spec-ctrl", "on" },
2152 { "model-id",
2153 "Intel Core i7 9xx (Nehalem Core i7, IBRS update)" },
2154 { /* end of list */ }
2157 { /* end of list */ }
2161 .name = "Westmere",
2162 .level = 11,
2163 .vendor = CPUID_VENDOR_INTEL,
2164 .family = 6,
2165 .model = 44,
2166 .stepping = 1,
2167 .features[FEAT_1_EDX] =
2168 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2169 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2170 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2171 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2172 CPUID_DE | CPUID_FP87,
2173 .features[FEAT_1_ECX] =
2174 CPUID_EXT_AES | CPUID_EXT_POPCNT | CPUID_EXT_SSE42 |
2175 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2176 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3,
2177 .features[FEAT_8000_0001_EDX] =
2178 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
2179 .features[FEAT_8000_0001_ECX] =
2180 CPUID_EXT3_LAHF_LM,
2181 .features[FEAT_6_EAX] =
2182 CPUID_6_EAX_ARAT,
2183 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2184 MSR_VMX_BASIC_TRUE_CTLS,
2185 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2186 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2187 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2188 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2189 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2190 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2191 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2192 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2193 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2194 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
2195 .features[FEAT_VMX_EXIT_CTLS] =
2196 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2197 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2198 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2199 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2200 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2201 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2202 MSR_VMX_MISC_STORE_LMA,
2203 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2204 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2205 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
2206 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2207 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2208 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2209 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2210 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2211 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2212 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2213 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2214 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2215 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2216 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2217 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2218 .features[FEAT_VMX_SECONDARY_CTLS] =
2219 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2220 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2221 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2222 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2223 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST,
2224 .xlevel = 0x80000008,
2225 .model_id = "Westmere E56xx/L56xx/X56xx (Nehalem-C)",
2226 .versions = (X86CPUVersionDefinition[]) {
2227 { .version = 1 },
2229 .version = 2,
2230 .alias = "Westmere-IBRS",
2231 .props = (PropValue[]) {
2232 { "spec-ctrl", "on" },
2233 { "model-id",
2234 "Westmere E56xx/L56xx/X56xx (IBRS update)" },
2235 { /* end of list */ }
2238 { /* end of list */ }
2242 .name = "SandyBridge",
2243 .level = 0xd,
2244 .vendor = CPUID_VENDOR_INTEL,
2245 .family = 6,
2246 .model = 42,
2247 .stepping = 1,
2248 .features[FEAT_1_EDX] =
2249 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2250 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2251 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2252 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2253 CPUID_DE | CPUID_FP87,
2254 .features[FEAT_1_ECX] =
2255 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2256 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_POPCNT |
2257 CPUID_EXT_X2APIC | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
2258 CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ |
2259 CPUID_EXT_SSE3,
2260 .features[FEAT_8000_0001_EDX] =
2261 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
2262 CPUID_EXT2_SYSCALL,
2263 .features[FEAT_8000_0001_ECX] =
2264 CPUID_EXT3_LAHF_LM,
2265 .features[FEAT_XSAVE] =
2266 CPUID_XSAVE_XSAVEOPT,
2267 .features[FEAT_6_EAX] =
2268 CPUID_6_EAX_ARAT,
2269 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2270 MSR_VMX_BASIC_TRUE_CTLS,
2271 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2272 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2273 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2274 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2275 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2276 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2277 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2278 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2279 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2280 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
2281 .features[FEAT_VMX_EXIT_CTLS] =
2282 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2283 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2284 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2285 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2286 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2287 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2288 MSR_VMX_MISC_STORE_LMA,
2289 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2290 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2291 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
2292 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2293 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2294 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2295 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2296 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2297 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2298 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2299 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2300 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2301 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2302 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2303 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2304 .features[FEAT_VMX_SECONDARY_CTLS] =
2305 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2306 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2307 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2308 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2309 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST,
2310 .xlevel = 0x80000008,
2311 .model_id = "Intel Xeon E312xx (Sandy Bridge)",
2312 .versions = (X86CPUVersionDefinition[]) {
2313 { .version = 1 },
2315 .version = 2,
2316 .alias = "SandyBridge-IBRS",
2317 .props = (PropValue[]) {
2318 { "spec-ctrl", "on" },
2319 { "model-id",
2320 "Intel Xeon E312xx (Sandy Bridge, IBRS update)" },
2321 { /* end of list */ }
2324 { /* end of list */ }
2328 .name = "IvyBridge",
2329 .level = 0xd,
2330 .vendor = CPUID_VENDOR_INTEL,
2331 .family = 6,
2332 .model = 58,
2333 .stepping = 9,
2334 .features[FEAT_1_EDX] =
2335 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2336 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2337 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2338 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2339 CPUID_DE | CPUID_FP87,
2340 .features[FEAT_1_ECX] =
2341 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2342 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_POPCNT |
2343 CPUID_EXT_X2APIC | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
2344 CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ |
2345 CPUID_EXT_SSE3 | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
2346 .features[FEAT_7_0_EBX] =
2347 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_SMEP |
2348 CPUID_7_0_EBX_ERMS,
2349 .features[FEAT_8000_0001_EDX] =
2350 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
2351 CPUID_EXT2_SYSCALL,
2352 .features[FEAT_8000_0001_ECX] =
2353 CPUID_EXT3_LAHF_LM,
2354 .features[FEAT_XSAVE] =
2355 CPUID_XSAVE_XSAVEOPT,
2356 .features[FEAT_6_EAX] =
2357 CPUID_6_EAX_ARAT,
2358 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2359 MSR_VMX_BASIC_TRUE_CTLS,
2360 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2361 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2362 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2363 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2364 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2365 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2366 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2367 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2368 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2369 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
2370 .features[FEAT_VMX_EXIT_CTLS] =
2371 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2372 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2373 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2374 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2375 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2376 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2377 MSR_VMX_MISC_STORE_LMA,
2378 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2379 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2380 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
2381 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2382 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2383 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2384 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2385 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2386 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2387 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2388 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2389 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2390 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2391 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2392 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2393 .features[FEAT_VMX_SECONDARY_CTLS] =
2394 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2395 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2396 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2397 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2398 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
2399 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
2400 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
2401 VMX_SECONDARY_EXEC_RDRAND_EXITING,
2402 .xlevel = 0x80000008,
2403 .model_id = "Intel Xeon E3-12xx v2 (Ivy Bridge)",
2404 .versions = (X86CPUVersionDefinition[]) {
2405 { .version = 1 },
2407 .version = 2,
2408 .alias = "IvyBridge-IBRS",
2409 .props = (PropValue[]) {
2410 { "spec-ctrl", "on" },
2411 { "model-id",
2412 "Intel Xeon E3-12xx v2 (Ivy Bridge, IBRS)" },
2413 { /* end of list */ }
2416 { /* end of list */ }
2420 .name = "Haswell",
2421 .level = 0xd,
2422 .vendor = CPUID_VENDOR_INTEL,
2423 .family = 6,
2424 .model = 60,
2425 .stepping = 4,
2426 .features[FEAT_1_EDX] =
2427 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2428 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2429 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2430 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2431 CPUID_DE | CPUID_FP87,
2432 .features[FEAT_1_ECX] =
2433 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2434 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
2435 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2436 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
2437 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
2438 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
2439 .features[FEAT_8000_0001_EDX] =
2440 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
2441 CPUID_EXT2_SYSCALL,
2442 .features[FEAT_8000_0001_ECX] =
2443 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM,
2444 .features[FEAT_7_0_EBX] =
2445 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
2446 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
2447 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
2448 CPUID_7_0_EBX_RTM,
2449 .features[FEAT_XSAVE] =
2450 CPUID_XSAVE_XSAVEOPT,
2451 .features[FEAT_6_EAX] =
2452 CPUID_6_EAX_ARAT,
2453 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2454 MSR_VMX_BASIC_TRUE_CTLS,
2455 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2456 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2457 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2458 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2459 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2460 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2461 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2462 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2463 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2464 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
2465 .features[FEAT_VMX_EXIT_CTLS] =
2466 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2467 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2468 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2469 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2470 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2471 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2472 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
2473 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2474 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2475 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
2476 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2477 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2478 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2479 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2480 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2481 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2482 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2483 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2484 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2485 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2486 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2487 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2488 .features[FEAT_VMX_SECONDARY_CTLS] =
2489 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2490 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2491 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2492 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2493 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
2494 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
2495 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
2496 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
2497 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS,
2498 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
2499 .xlevel = 0x80000008,
2500 .model_id = "Intel Core Processor (Haswell)",
2501 .versions = (X86CPUVersionDefinition[]) {
2502 { .version = 1 },
2504 .version = 2,
2505 .alias = "Haswell-noTSX",
2506 .props = (PropValue[]) {
2507 { "hle", "off" },
2508 { "rtm", "off" },
2509 { "stepping", "1" },
2510 { "model-id", "Intel Core Processor (Haswell, no TSX)", },
2511 { /* end of list */ }
2515 .version = 3,
2516 .alias = "Haswell-IBRS",
2517 .props = (PropValue[]) {
2518 /* Restore TSX features removed by -v2 above */
2519 { "hle", "on" },
2520 { "rtm", "on" },
2522 * Haswell and Haswell-IBRS had stepping=4 in
2523 * QEMU 4.0 and older
2525 { "stepping", "4" },
2526 { "spec-ctrl", "on" },
2527 { "model-id",
2528 "Intel Core Processor (Haswell, IBRS)" },
2529 { /* end of list */ }
2533 .version = 4,
2534 .alias = "Haswell-noTSX-IBRS",
2535 .props = (PropValue[]) {
2536 { "hle", "off" },
2537 { "rtm", "off" },
2538 /* spec-ctrl was already enabled by -v3 above */
2539 { "stepping", "1" },
2540 { "model-id",
2541 "Intel Core Processor (Haswell, no TSX, IBRS)" },
2542 { /* end of list */ }
2545 { /* end of list */ }
2549 .name = "Broadwell",
2550 .level = 0xd,
2551 .vendor = CPUID_VENDOR_INTEL,
2552 .family = 6,
2553 .model = 61,
2554 .stepping = 2,
2555 .features[FEAT_1_EDX] =
2556 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2557 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2558 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2559 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2560 CPUID_DE | CPUID_FP87,
2561 .features[FEAT_1_ECX] =
2562 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2563 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
2564 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2565 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
2566 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
2567 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
2568 .features[FEAT_8000_0001_EDX] =
2569 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
2570 CPUID_EXT2_SYSCALL,
2571 .features[FEAT_8000_0001_ECX] =
2572 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
2573 .features[FEAT_7_0_EBX] =
2574 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
2575 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
2576 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
2577 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
2578 CPUID_7_0_EBX_SMAP,
2579 .features[FEAT_XSAVE] =
2580 CPUID_XSAVE_XSAVEOPT,
2581 .features[FEAT_6_EAX] =
2582 CPUID_6_EAX_ARAT,
2583 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2584 MSR_VMX_BASIC_TRUE_CTLS,
2585 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2586 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2587 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2588 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2589 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2590 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2591 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2592 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2593 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2594 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
2595 .features[FEAT_VMX_EXIT_CTLS] =
2596 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2597 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2598 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2599 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2600 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2601 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2602 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
2603 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2604 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2605 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
2606 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2607 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2608 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2609 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2610 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2611 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2612 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2613 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2614 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2615 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2616 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2617 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2618 .features[FEAT_VMX_SECONDARY_CTLS] =
2619 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2620 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2621 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2622 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2623 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
2624 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
2625 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
2626 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
2627 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
2628 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
2629 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
2630 .xlevel = 0x80000008,
2631 .model_id = "Intel Core Processor (Broadwell)",
2632 .versions = (X86CPUVersionDefinition[]) {
2633 { .version = 1 },
2635 .version = 2,
2636 .alias = "Broadwell-noTSX",
2637 .props = (PropValue[]) {
2638 { "hle", "off" },
2639 { "rtm", "off" },
2640 { "model-id", "Intel Core Processor (Broadwell, no TSX)", },
2641 { /* end of list */ }
2645 .version = 3,
2646 .alias = "Broadwell-IBRS",
2647 .props = (PropValue[]) {
2648 /* Restore TSX features removed by -v2 above */
2649 { "hle", "on" },
2650 { "rtm", "on" },
2651 { "spec-ctrl", "on" },
2652 { "model-id",
2653 "Intel Core Processor (Broadwell, IBRS)" },
2654 { /* end of list */ }
2658 .version = 4,
2659 .alias = "Broadwell-noTSX-IBRS",
2660 .props = (PropValue[]) {
2661 { "hle", "off" },
2662 { "rtm", "off" },
2663 /* spec-ctrl was already enabled by -v3 above */
2664 { "model-id",
2665 "Intel Core Processor (Broadwell, no TSX, IBRS)" },
2666 { /* end of list */ }
2669 { /* end of list */ }
2673 .name = "Skylake-Client",
2674 .level = 0xd,
2675 .vendor = CPUID_VENDOR_INTEL,
2676 .family = 6,
2677 .model = 94,
2678 .stepping = 3,
2679 .features[FEAT_1_EDX] =
2680 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2681 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2682 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2683 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2684 CPUID_DE | CPUID_FP87,
2685 .features[FEAT_1_ECX] =
2686 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2687 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
2688 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2689 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
2690 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
2691 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
2692 .features[FEAT_8000_0001_EDX] =
2693 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
2694 CPUID_EXT2_SYSCALL,
2695 .features[FEAT_8000_0001_ECX] =
2696 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
2697 .features[FEAT_7_0_EBX] =
2698 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
2699 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
2700 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
2701 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
2702 CPUID_7_0_EBX_SMAP,
2703 /* XSAVES is added in version 4 */
2704 .features[FEAT_XSAVE] =
2705 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
2706 CPUID_XSAVE_XGETBV1,
2707 .features[FEAT_6_EAX] =
2708 CPUID_6_EAX_ARAT,
2709 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
2710 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2711 MSR_VMX_BASIC_TRUE_CTLS,
2712 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2713 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2714 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2715 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2716 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2717 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2718 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2719 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2720 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2721 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
2722 .features[FEAT_VMX_EXIT_CTLS] =
2723 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2724 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2725 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2726 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2727 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2728 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2729 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
2730 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2731 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2732 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
2733 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2734 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2735 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2736 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2737 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2738 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2739 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2740 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2741 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2742 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2743 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2744 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2745 .features[FEAT_VMX_SECONDARY_CTLS] =
2746 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2747 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2748 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2749 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
2750 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
2751 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
2752 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
2753 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
2754 .xlevel = 0x80000008,
2755 .model_id = "Intel Core Processor (Skylake)",
2756 .versions = (X86CPUVersionDefinition[]) {
2757 { .version = 1 },
2759 .version = 2,
2760 .alias = "Skylake-Client-IBRS",
2761 .props = (PropValue[]) {
2762 { "spec-ctrl", "on" },
2763 { "model-id",
2764 "Intel Core Processor (Skylake, IBRS)" },
2765 { /* end of list */ }
2769 .version = 3,
2770 .alias = "Skylake-Client-noTSX-IBRS",
2771 .props = (PropValue[]) {
2772 { "hle", "off" },
2773 { "rtm", "off" },
2774 { "model-id",
2775 "Intel Core Processor (Skylake, IBRS, no TSX)" },
2776 { /* end of list */ }
2780 .version = 4,
2781 .note = "IBRS, XSAVES, no TSX",
2782 .props = (PropValue[]) {
2783 { "xsaves", "on" },
2784 { "vmx-xsaves", "on" },
2785 { /* end of list */ }
2788 { /* end of list */ }
2792 .name = "Skylake-Server",
2793 .level = 0xd,
2794 .vendor = CPUID_VENDOR_INTEL,
2795 .family = 6,
2796 .model = 85,
2797 .stepping = 4,
2798 .features[FEAT_1_EDX] =
2799 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2800 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2801 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2802 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2803 CPUID_DE | CPUID_FP87,
2804 .features[FEAT_1_ECX] =
2805 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2806 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
2807 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2808 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
2809 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
2810 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
2811 .features[FEAT_8000_0001_EDX] =
2812 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
2813 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
2814 .features[FEAT_8000_0001_ECX] =
2815 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
2816 .features[FEAT_7_0_EBX] =
2817 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
2818 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
2819 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
2820 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
2821 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLWB |
2822 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
2823 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512CD |
2824 CPUID_7_0_EBX_AVX512VL | CPUID_7_0_EBX_CLFLUSHOPT,
2825 .features[FEAT_7_0_ECX] =
2826 CPUID_7_0_ECX_PKU,
2827 /* XSAVES is added in version 5 */
2828 .features[FEAT_XSAVE] =
2829 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
2830 CPUID_XSAVE_XGETBV1,
2831 .features[FEAT_6_EAX] =
2832 CPUID_6_EAX_ARAT,
2833 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
2834 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2835 MSR_VMX_BASIC_TRUE_CTLS,
2836 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2837 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2838 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2839 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2840 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2841 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2842 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2843 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2844 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2845 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
2846 .features[FEAT_VMX_EXIT_CTLS] =
2847 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2848 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2849 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2850 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2851 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2852 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2853 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
2854 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2855 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2856 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
2857 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2858 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2859 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2860 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2861 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2862 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2863 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2864 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2865 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2866 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2867 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2868 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2869 .features[FEAT_VMX_SECONDARY_CTLS] =
2870 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2871 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2872 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2873 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2874 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
2875 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
2876 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
2877 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
2878 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
2879 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
2880 .xlevel = 0x80000008,
2881 .model_id = "Intel Xeon Processor (Skylake)",
2882 .versions = (X86CPUVersionDefinition[]) {
2883 { .version = 1 },
2885 .version = 2,
2886 .alias = "Skylake-Server-IBRS",
2887 .props = (PropValue[]) {
2888 /* clflushopt was not added to Skylake-Server-IBRS */
2889 /* TODO: add -v3 including clflushopt */
2890 { "clflushopt", "off" },
2891 { "spec-ctrl", "on" },
2892 { "model-id",
2893 "Intel Xeon Processor (Skylake, IBRS)" },
2894 { /* end of list */ }
2898 .version = 3,
2899 .alias = "Skylake-Server-noTSX-IBRS",
2900 .props = (PropValue[]) {
2901 { "hle", "off" },
2902 { "rtm", "off" },
2903 { "model-id",
2904 "Intel Xeon Processor (Skylake, IBRS, no TSX)" },
2905 { /* end of list */ }
2909 .version = 4,
2910 .props = (PropValue[]) {
2911 { "vmx-eptp-switching", "on" },
2912 { /* end of list */ }
2916 .version = 5,
2917 .note = "IBRS, XSAVES, EPT switching, no TSX",
2918 .props = (PropValue[]) {
2919 { "xsaves", "on" },
2920 { "vmx-xsaves", "on" },
2921 { /* end of list */ }
2924 { /* end of list */ }
2928 .name = "Cascadelake-Server",
2929 .level = 0xd,
2930 .vendor = CPUID_VENDOR_INTEL,
2931 .family = 6,
2932 .model = 85,
2933 .stepping = 6,
2934 .features[FEAT_1_EDX] =
2935 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2936 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2937 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2938 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2939 CPUID_DE | CPUID_FP87,
2940 .features[FEAT_1_ECX] =
2941 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2942 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
2943 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2944 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
2945 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
2946 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
2947 .features[FEAT_8000_0001_EDX] =
2948 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
2949 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
2950 .features[FEAT_8000_0001_ECX] =
2951 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
2952 .features[FEAT_7_0_EBX] =
2953 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
2954 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
2955 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
2956 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
2957 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLWB |
2958 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
2959 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512CD |
2960 CPUID_7_0_EBX_AVX512VL | CPUID_7_0_EBX_CLFLUSHOPT,
2961 .features[FEAT_7_0_ECX] =
2962 CPUID_7_0_ECX_PKU |
2963 CPUID_7_0_ECX_AVX512VNNI,
2964 .features[FEAT_7_0_EDX] =
2965 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_SPEC_CTRL_SSBD,
2966 /* XSAVES is added in version 5 */
2967 .features[FEAT_XSAVE] =
2968 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
2969 CPUID_XSAVE_XGETBV1,
2970 .features[FEAT_6_EAX] =
2971 CPUID_6_EAX_ARAT,
2972 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
2973 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2974 MSR_VMX_BASIC_TRUE_CTLS,
2975 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2976 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2977 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2978 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2979 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2980 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2981 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2982 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2983 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2984 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
2985 .features[FEAT_VMX_EXIT_CTLS] =
2986 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2987 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2988 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2989 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2990 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2991 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2992 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
2993 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2994 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2995 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
2996 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2997 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2998 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2999 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3000 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3001 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3002 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3003 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3004 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3005 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3006 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3007 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3008 .features[FEAT_VMX_SECONDARY_CTLS] =
3009 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3010 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3011 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3012 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3013 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3014 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3015 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3016 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3017 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3018 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3019 .xlevel = 0x80000008,
3020 .model_id = "Intel Xeon Processor (Cascadelake)",
3021 .versions = (X86CPUVersionDefinition[]) {
3022 { .version = 1 },
3023 { .version = 2,
3024 .note = "ARCH_CAPABILITIES",
3025 .props = (PropValue[]) {
3026 { "arch-capabilities", "on" },
3027 { "rdctl-no", "on" },
3028 { "ibrs-all", "on" },
3029 { "skip-l1dfl-vmentry", "on" },
3030 { "mds-no", "on" },
3031 { /* end of list */ }
3034 { .version = 3,
3035 .alias = "Cascadelake-Server-noTSX",
3036 .note = "ARCH_CAPABILITIES, no TSX",
3037 .props = (PropValue[]) {
3038 { "hle", "off" },
3039 { "rtm", "off" },
3040 { /* end of list */ }
3043 { .version = 4,
3044 .note = "ARCH_CAPABILITIES, no TSX",
3045 .props = (PropValue[]) {
3046 { "vmx-eptp-switching", "on" },
3047 { /* end of list */ }
3050 { .version = 5,
3051 .note = "ARCH_CAPABILITIES, EPT switching, XSAVES, no TSX",
3052 .props = (PropValue[]) {
3053 { "xsaves", "on" },
3054 { "vmx-xsaves", "on" },
3055 { /* end of list */ }
3058 { /* end of list */ }
3062 .name = "Cooperlake",
3063 .level = 0xd,
3064 .vendor = CPUID_VENDOR_INTEL,
3065 .family = 6,
3066 .model = 85,
3067 .stepping = 10,
3068 .features[FEAT_1_EDX] =
3069 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3070 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3071 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3072 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3073 CPUID_DE | CPUID_FP87,
3074 .features[FEAT_1_ECX] =
3075 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3076 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3077 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3078 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3079 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3080 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3081 .features[FEAT_8000_0001_EDX] =
3082 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
3083 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3084 .features[FEAT_8000_0001_ECX] =
3085 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3086 .features[FEAT_7_0_EBX] =
3087 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
3088 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
3089 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
3090 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
3091 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLWB |
3092 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
3093 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512CD |
3094 CPUID_7_0_EBX_AVX512VL | CPUID_7_0_EBX_CLFLUSHOPT,
3095 .features[FEAT_7_0_ECX] =
3096 CPUID_7_0_ECX_PKU |
3097 CPUID_7_0_ECX_AVX512VNNI,
3098 .features[FEAT_7_0_EDX] =
3099 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_STIBP |
3100 CPUID_7_0_EDX_SPEC_CTRL_SSBD | CPUID_7_0_EDX_ARCH_CAPABILITIES,
3101 .features[FEAT_ARCH_CAPABILITIES] =
3102 MSR_ARCH_CAP_RDCL_NO | MSR_ARCH_CAP_IBRS_ALL |
3103 MSR_ARCH_CAP_SKIP_L1DFL_VMENTRY | MSR_ARCH_CAP_MDS_NO |
3104 MSR_ARCH_CAP_PSCHANGE_MC_NO | MSR_ARCH_CAP_TAA_NO,
3105 .features[FEAT_7_1_EAX] =
3106 CPUID_7_1_EAX_AVX512_BF16,
3107 /* XSAVES is added in version 2 */
3108 .features[FEAT_XSAVE] =
3109 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3110 CPUID_XSAVE_XGETBV1,
3111 .features[FEAT_6_EAX] =
3112 CPUID_6_EAX_ARAT,
3113 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
3114 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3115 MSR_VMX_BASIC_TRUE_CTLS,
3116 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3117 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3118 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3119 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3120 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3121 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3122 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3123 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3124 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3125 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3126 .features[FEAT_VMX_EXIT_CTLS] =
3127 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3128 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3129 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3130 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3131 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3132 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3133 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3134 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3135 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3136 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3137 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3138 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3139 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3140 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3141 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3142 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3143 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3144 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3145 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3146 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3147 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3148 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3149 .features[FEAT_VMX_SECONDARY_CTLS] =
3150 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3151 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3152 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3153 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3154 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3155 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3156 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3157 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3158 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3159 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3160 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
3161 .xlevel = 0x80000008,
3162 .model_id = "Intel Xeon Processor (Cooperlake)",
3163 .versions = (X86CPUVersionDefinition[]) {
3164 { .version = 1 },
3165 { .version = 2,
3166 .note = "XSAVES",
3167 .props = (PropValue[]) {
3168 { "xsaves", "on" },
3169 { "vmx-xsaves", "on" },
3170 { /* end of list */ }
3173 { /* end of list */ }
3177 .name = "Icelake-Client",
3178 .level = 0xd,
3179 .vendor = CPUID_VENDOR_INTEL,
3180 .family = 6,
3181 .model = 126,
3182 .stepping = 0,
3183 .features[FEAT_1_EDX] =
3184 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3185 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3186 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3187 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3188 CPUID_DE | CPUID_FP87,
3189 .features[FEAT_1_ECX] =
3190 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3191 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3192 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3193 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3194 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3195 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3196 .features[FEAT_8000_0001_EDX] =
3197 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
3198 CPUID_EXT2_SYSCALL,
3199 .features[FEAT_8000_0001_ECX] =
3200 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3201 .features[FEAT_8000_0008_EBX] =
3202 CPUID_8000_0008_EBX_WBNOINVD,
3203 .features[FEAT_7_0_EBX] =
3204 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
3205 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
3206 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
3207 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
3208 CPUID_7_0_EBX_SMAP,
3209 .features[FEAT_7_0_ECX] =
3210 CPUID_7_0_ECX_AVX512_VBMI | CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_PKU |
3211 CPUID_7_0_ECX_AVX512_VBMI2 | CPUID_7_0_ECX_GFNI |
3212 CPUID_7_0_ECX_VAES | CPUID_7_0_ECX_VPCLMULQDQ |
3213 CPUID_7_0_ECX_AVX512VNNI | CPUID_7_0_ECX_AVX512BITALG |
3214 CPUID_7_0_ECX_AVX512_VPOPCNTDQ,
3215 .features[FEAT_7_0_EDX] =
3216 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_SPEC_CTRL_SSBD,
3217 /* XSAVES is added in version 3 */
3218 .features[FEAT_XSAVE] =
3219 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3220 CPUID_XSAVE_XGETBV1,
3221 .features[FEAT_6_EAX] =
3222 CPUID_6_EAX_ARAT,
3223 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
3224 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3225 MSR_VMX_BASIC_TRUE_CTLS,
3226 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3227 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3228 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3229 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3230 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3231 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3232 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3233 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3234 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3235 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3236 .features[FEAT_VMX_EXIT_CTLS] =
3237 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3238 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3239 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3240 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3241 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3242 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3243 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3244 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3245 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3246 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
3247 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3248 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3249 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3250 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3251 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3252 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3253 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3254 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3255 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3256 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3257 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3258 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3259 .features[FEAT_VMX_SECONDARY_CTLS] =
3260 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3261 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3262 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3263 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3264 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3265 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3266 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3267 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
3268 .xlevel = 0x80000008,
3269 .model_id = "Intel Core Processor (Icelake)",
3270 .versions = (X86CPUVersionDefinition[]) {
3272 .version = 1,
3273 .note = "deprecated"
3276 .version = 2,
3277 .note = "no TSX, deprecated",
3278 .alias = "Icelake-Client-noTSX",
3279 .props = (PropValue[]) {
3280 { "hle", "off" },
3281 { "rtm", "off" },
3282 { /* end of list */ }
3286 .version = 3,
3287 .note = "no TSX, XSAVES, deprecated",
3288 .props = (PropValue[]) {
3289 { "xsaves", "on" },
3290 { "vmx-xsaves", "on" },
3291 { /* end of list */ }
3294 { /* end of list */ }
3296 .deprecation_note = "use Icelake-Server instead"
3299 .name = "Icelake-Server",
3300 .level = 0xd,
3301 .vendor = CPUID_VENDOR_INTEL,
3302 .family = 6,
3303 .model = 134,
3304 .stepping = 0,
3305 .features[FEAT_1_EDX] =
3306 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3307 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3308 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3309 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3310 CPUID_DE | CPUID_FP87,
3311 .features[FEAT_1_ECX] =
3312 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3313 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3314 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3315 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3316 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3317 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3318 .features[FEAT_8000_0001_EDX] =
3319 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
3320 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3321 .features[FEAT_8000_0001_ECX] =
3322 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3323 .features[FEAT_8000_0008_EBX] =
3324 CPUID_8000_0008_EBX_WBNOINVD,
3325 .features[FEAT_7_0_EBX] =
3326 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
3327 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
3328 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
3329 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
3330 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLWB |
3331 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
3332 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512CD |
3333 CPUID_7_0_EBX_AVX512VL | CPUID_7_0_EBX_CLFLUSHOPT,
3334 .features[FEAT_7_0_ECX] =
3335 CPUID_7_0_ECX_AVX512_VBMI | CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_PKU |
3336 CPUID_7_0_ECX_AVX512_VBMI2 | CPUID_7_0_ECX_GFNI |
3337 CPUID_7_0_ECX_VAES | CPUID_7_0_ECX_VPCLMULQDQ |
3338 CPUID_7_0_ECX_AVX512VNNI | CPUID_7_0_ECX_AVX512BITALG |
3339 CPUID_7_0_ECX_AVX512_VPOPCNTDQ | CPUID_7_0_ECX_LA57,
3340 .features[FEAT_7_0_EDX] =
3341 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_SPEC_CTRL_SSBD,
3342 /* XSAVES is added in version 5 */
3343 .features[FEAT_XSAVE] =
3344 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3345 CPUID_XSAVE_XGETBV1,
3346 .features[FEAT_6_EAX] =
3347 CPUID_6_EAX_ARAT,
3348 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
3349 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3350 MSR_VMX_BASIC_TRUE_CTLS,
3351 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3352 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3353 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3354 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3355 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3356 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3357 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3358 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3359 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3360 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3361 .features[FEAT_VMX_EXIT_CTLS] =
3362 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3363 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3364 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3365 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3366 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3367 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3368 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3369 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3370 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3371 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3372 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3373 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3374 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3375 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3376 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3377 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3378 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3379 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3380 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3381 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3382 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3383 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3384 .features[FEAT_VMX_SECONDARY_CTLS] =
3385 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3386 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3387 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3388 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3389 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3390 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3391 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3392 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3393 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS,
3394 .xlevel = 0x80000008,
3395 .model_id = "Intel Xeon Processor (Icelake)",
3396 .versions = (X86CPUVersionDefinition[]) {
3397 { .version = 1 },
3399 .version = 2,
3400 .note = "no TSX",
3401 .alias = "Icelake-Server-noTSX",
3402 .props = (PropValue[]) {
3403 { "hle", "off" },
3404 { "rtm", "off" },
3405 { /* end of list */ }
3409 .version = 3,
3410 .props = (PropValue[]) {
3411 { "arch-capabilities", "on" },
3412 { "rdctl-no", "on" },
3413 { "ibrs-all", "on" },
3414 { "skip-l1dfl-vmentry", "on" },
3415 { "mds-no", "on" },
3416 { "pschange-mc-no", "on" },
3417 { "taa-no", "on" },
3418 { /* end of list */ }
3422 .version = 4,
3423 .props = (PropValue[]) {
3424 { "sha-ni", "on" },
3425 { "avx512ifma", "on" },
3426 { "rdpid", "on" },
3427 { "fsrm", "on" },
3428 { "vmx-rdseed-exit", "on" },
3429 { "vmx-pml", "on" },
3430 { "vmx-eptp-switching", "on" },
3431 { "model", "106" },
3432 { /* end of list */ }
3436 .version = 5,
3437 .note = "XSAVES",
3438 .props = (PropValue[]) {
3439 { "xsaves", "on" },
3440 { "vmx-xsaves", "on" },
3441 { /* end of list */ }
3444 { /* end of list */ }
3448 .name = "Denverton",
3449 .level = 21,
3450 .vendor = CPUID_VENDOR_INTEL,
3451 .family = 6,
3452 .model = 95,
3453 .stepping = 1,
3454 .features[FEAT_1_EDX] =
3455 CPUID_FP87 | CPUID_VME | CPUID_DE | CPUID_PSE | CPUID_TSC |
3456 CPUID_MSR | CPUID_PAE | CPUID_MCE | CPUID_CX8 | CPUID_APIC |
3457 CPUID_SEP | CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV |
3458 CPUID_PAT | CPUID_PSE36 | CPUID_CLFLUSH | CPUID_MMX | CPUID_FXSR |
3459 CPUID_SSE | CPUID_SSE2,
3460 .features[FEAT_1_ECX] =
3461 CPUID_EXT_SSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_MONITOR |
3462 CPUID_EXT_SSSE3 | CPUID_EXT_CX16 | CPUID_EXT_SSE41 |
3463 CPUID_EXT_SSE42 | CPUID_EXT_X2APIC | CPUID_EXT_MOVBE |
3464 CPUID_EXT_POPCNT | CPUID_EXT_TSC_DEADLINE_TIMER |
3465 CPUID_EXT_AES | CPUID_EXT_XSAVE | CPUID_EXT_RDRAND,
3466 .features[FEAT_8000_0001_EDX] =
3467 CPUID_EXT2_SYSCALL | CPUID_EXT2_NX | CPUID_EXT2_PDPE1GB |
3468 CPUID_EXT2_RDTSCP | CPUID_EXT2_LM,
3469 .features[FEAT_8000_0001_ECX] =
3470 CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3471 .features[FEAT_7_0_EBX] =
3472 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_ERMS |
3473 CPUID_7_0_EBX_MPX | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_SMAP |
3474 CPUID_7_0_EBX_CLFLUSHOPT | CPUID_7_0_EBX_SHA_NI,
3475 .features[FEAT_7_0_EDX] =
3476 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_ARCH_CAPABILITIES |
3477 CPUID_7_0_EDX_SPEC_CTRL_SSBD,
3478 /* XSAVES is added in version 3 */
3479 .features[FEAT_XSAVE] =
3480 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC | CPUID_XSAVE_XGETBV1,
3481 .features[FEAT_6_EAX] =
3482 CPUID_6_EAX_ARAT,
3483 .features[FEAT_ARCH_CAPABILITIES] =
3484 MSR_ARCH_CAP_RDCL_NO | MSR_ARCH_CAP_SKIP_L1DFL_VMENTRY,
3485 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3486 MSR_VMX_BASIC_TRUE_CTLS,
3487 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3488 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3489 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3490 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3491 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3492 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3493 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3494 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3495 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3496 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3497 .features[FEAT_VMX_EXIT_CTLS] =
3498 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3499 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3500 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3501 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3502 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3503 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3504 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3505 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3506 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3507 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3508 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3509 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3510 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3511 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3512 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3513 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3514 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3515 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3516 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3517 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3518 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3519 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3520 .features[FEAT_VMX_SECONDARY_CTLS] =
3521 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3522 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3523 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3524 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3525 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3526 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3527 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3528 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3529 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3530 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3531 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
3532 .xlevel = 0x80000008,
3533 .model_id = "Intel Atom Processor (Denverton)",
3534 .versions = (X86CPUVersionDefinition[]) {
3535 { .version = 1 },
3537 .version = 2,
3538 .note = "no MPX, no MONITOR",
3539 .props = (PropValue[]) {
3540 { "monitor", "off" },
3541 { "mpx", "off" },
3542 { /* end of list */ },
3546 .version = 3,
3547 .note = "XSAVES, no MPX, no MONITOR",
3548 .props = (PropValue[]) {
3549 { "xsaves", "on" },
3550 { "vmx-xsaves", "on" },
3551 { /* end of list */ },
3554 { /* end of list */ },
3558 .name = "Snowridge",
3559 .level = 27,
3560 .vendor = CPUID_VENDOR_INTEL,
3561 .family = 6,
3562 .model = 134,
3563 .stepping = 1,
3564 .features[FEAT_1_EDX] =
3565 /* missing: CPUID_PN CPUID_IA64 */
3566 /* missing: CPUID_DTS, CPUID_HT, CPUID_TM, CPUID_PBE */
3567 CPUID_FP87 | CPUID_VME | CPUID_DE | CPUID_PSE |
3568 CPUID_TSC | CPUID_MSR | CPUID_PAE | CPUID_MCE |
3569 CPUID_CX8 | CPUID_APIC | CPUID_SEP |
3570 CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV |
3571 CPUID_PAT | CPUID_PSE36 | CPUID_CLFLUSH |
3572 CPUID_MMX |
3573 CPUID_FXSR | CPUID_SSE | CPUID_SSE2,
3574 .features[FEAT_1_ECX] =
3575 CPUID_EXT_SSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_MONITOR |
3576 CPUID_EXT_SSSE3 |
3577 CPUID_EXT_CX16 |
3578 CPUID_EXT_SSE41 |
3579 CPUID_EXT_SSE42 | CPUID_EXT_X2APIC | CPUID_EXT_MOVBE |
3580 CPUID_EXT_POPCNT |
3581 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_AES | CPUID_EXT_XSAVE |
3582 CPUID_EXT_RDRAND,
3583 .features[FEAT_8000_0001_EDX] =
3584 CPUID_EXT2_SYSCALL |
3585 CPUID_EXT2_NX |
3586 CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
3587 CPUID_EXT2_LM,
3588 .features[FEAT_8000_0001_ECX] =
3589 CPUID_EXT3_LAHF_LM |
3590 CPUID_EXT3_3DNOWPREFETCH,
3591 .features[FEAT_7_0_EBX] =
3592 CPUID_7_0_EBX_FSGSBASE |
3593 CPUID_7_0_EBX_SMEP |
3594 CPUID_7_0_EBX_ERMS |
3595 CPUID_7_0_EBX_MPX | /* missing bits 13, 15 */
3596 CPUID_7_0_EBX_RDSEED |
3597 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT |
3598 CPUID_7_0_EBX_CLWB |
3599 CPUID_7_0_EBX_SHA_NI,
3600 .features[FEAT_7_0_ECX] =
3601 CPUID_7_0_ECX_UMIP |
3602 /* missing bit 5 */
3603 CPUID_7_0_ECX_GFNI |
3604 CPUID_7_0_ECX_MOVDIRI | CPUID_7_0_ECX_CLDEMOTE |
3605 CPUID_7_0_ECX_MOVDIR64B,
3606 .features[FEAT_7_0_EDX] =
3607 CPUID_7_0_EDX_SPEC_CTRL |
3608 CPUID_7_0_EDX_ARCH_CAPABILITIES | CPUID_7_0_EDX_SPEC_CTRL_SSBD |
3609 CPUID_7_0_EDX_CORE_CAPABILITY,
3610 .features[FEAT_CORE_CAPABILITY] =
3611 MSR_CORE_CAP_SPLIT_LOCK_DETECT,
3612 /* XSAVES is is added in version 3 */
3613 .features[FEAT_XSAVE] =
3614 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3615 CPUID_XSAVE_XGETBV1,
3616 .features[FEAT_6_EAX] =
3617 CPUID_6_EAX_ARAT,
3618 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3619 MSR_VMX_BASIC_TRUE_CTLS,
3620 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3621 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3622 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3623 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3624 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3625 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3626 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3627 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3628 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3629 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3630 .features[FEAT_VMX_EXIT_CTLS] =
3631 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3632 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3633 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3634 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3635 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3636 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3637 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3638 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3639 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3640 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3641 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3642 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3643 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3644 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3645 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3646 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3647 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3648 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3649 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3650 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3651 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3652 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3653 .features[FEAT_VMX_SECONDARY_CTLS] =
3654 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3655 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3656 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3657 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3658 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3659 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3660 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3661 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3662 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3663 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3664 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
3665 .xlevel = 0x80000008,
3666 .model_id = "Intel Atom Processor (SnowRidge)",
3667 .versions = (X86CPUVersionDefinition[]) {
3668 { .version = 1 },
3670 .version = 2,
3671 .props = (PropValue[]) {
3672 { "mpx", "off" },
3673 { "model-id", "Intel Atom Processor (Snowridge, no MPX)" },
3674 { /* end of list */ },
3678 .version = 3,
3679 .note = "XSAVES, no MPX",
3680 .props = (PropValue[]) {
3681 { "xsaves", "on" },
3682 { "vmx-xsaves", "on" },
3683 { /* end of list */ },
3687 .version = 4,
3688 .note = "no split lock detect",
3689 .props = (PropValue[]) {
3690 { "split-lock-detect", "off" },
3691 { /* end of list */ },
3694 { /* end of list */ },
3698 .name = "KnightsMill",
3699 .level = 0xd,
3700 .vendor = CPUID_VENDOR_INTEL,
3701 .family = 6,
3702 .model = 133,
3703 .stepping = 0,
3704 .features[FEAT_1_EDX] =
3705 CPUID_VME | CPUID_SS | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR |
3706 CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV |
3707 CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC |
3708 CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC |
3709 CPUID_PSE | CPUID_DE | CPUID_FP87,
3710 .features[FEAT_1_ECX] =
3711 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3712 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3713 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3714 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3715 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3716 CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3717 .features[FEAT_8000_0001_EDX] =
3718 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
3719 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3720 .features[FEAT_8000_0001_ECX] =
3721 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3722 .features[FEAT_7_0_EBX] =
3723 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
3724 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS |
3725 CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_AVX512F |
3726 CPUID_7_0_EBX_AVX512CD | CPUID_7_0_EBX_AVX512PF |
3727 CPUID_7_0_EBX_AVX512ER,
3728 .features[FEAT_7_0_ECX] =
3729 CPUID_7_0_ECX_AVX512_VPOPCNTDQ,
3730 .features[FEAT_7_0_EDX] =
3731 CPUID_7_0_EDX_AVX512_4VNNIW | CPUID_7_0_EDX_AVX512_4FMAPS,
3732 .features[FEAT_XSAVE] =
3733 CPUID_XSAVE_XSAVEOPT,
3734 .features[FEAT_6_EAX] =
3735 CPUID_6_EAX_ARAT,
3736 .xlevel = 0x80000008,
3737 .model_id = "Intel Xeon Phi Processor (Knights Mill)",
3740 .name = "Opteron_G1",
3741 .level = 5,
3742 .vendor = CPUID_VENDOR_AMD,
3743 .family = 15,
3744 .model = 6,
3745 .stepping = 1,
3746 .features[FEAT_1_EDX] =
3747 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3748 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3749 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3750 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3751 CPUID_DE | CPUID_FP87,
3752 .features[FEAT_1_ECX] =
3753 CPUID_EXT_SSE3,
3754 .features[FEAT_8000_0001_EDX] =
3755 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3756 .xlevel = 0x80000008,
3757 .model_id = "AMD Opteron 240 (Gen 1 Class Opteron)",
3760 .name = "Opteron_G2",
3761 .level = 5,
3762 .vendor = CPUID_VENDOR_AMD,
3763 .family = 15,
3764 .model = 6,
3765 .stepping = 1,
3766 .features[FEAT_1_EDX] =
3767 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3768 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3769 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3770 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3771 CPUID_DE | CPUID_FP87,
3772 .features[FEAT_1_ECX] =
3773 CPUID_EXT_CX16 | CPUID_EXT_SSE3,
3774 .features[FEAT_8000_0001_EDX] =
3775 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3776 .features[FEAT_8000_0001_ECX] =
3777 CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM,
3778 .xlevel = 0x80000008,
3779 .model_id = "AMD Opteron 22xx (Gen 2 Class Opteron)",
3782 .name = "Opteron_G3",
3783 .level = 5,
3784 .vendor = CPUID_VENDOR_AMD,
3785 .family = 16,
3786 .model = 2,
3787 .stepping = 3,
3788 .features[FEAT_1_EDX] =
3789 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3790 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3791 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3792 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3793 CPUID_DE | CPUID_FP87,
3794 .features[FEAT_1_ECX] =
3795 CPUID_EXT_POPCNT | CPUID_EXT_CX16 | CPUID_EXT_MONITOR |
3796 CPUID_EXT_SSE3,
3797 .features[FEAT_8000_0001_EDX] =
3798 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL |
3799 CPUID_EXT2_RDTSCP,
3800 .features[FEAT_8000_0001_ECX] =
3801 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A |
3802 CPUID_EXT3_ABM | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM,
3803 .xlevel = 0x80000008,
3804 .model_id = "AMD Opteron 23xx (Gen 3 Class Opteron)",
3807 .name = "Opteron_G4",
3808 .level = 0xd,
3809 .vendor = CPUID_VENDOR_AMD,
3810 .family = 21,
3811 .model = 1,
3812 .stepping = 2,
3813 .features[FEAT_1_EDX] =
3814 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3815 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3816 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3817 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3818 CPUID_DE | CPUID_FP87,
3819 .features[FEAT_1_ECX] =
3820 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3821 CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
3822 CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ |
3823 CPUID_EXT_SSE3,
3824 .features[FEAT_8000_0001_EDX] =
3825 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_NX |
3826 CPUID_EXT2_SYSCALL | CPUID_EXT2_RDTSCP,
3827 .features[FEAT_8000_0001_ECX] =
3828 CPUID_EXT3_FMA4 | CPUID_EXT3_XOP |
3829 CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_MISALIGNSSE |
3830 CPUID_EXT3_SSE4A | CPUID_EXT3_ABM | CPUID_EXT3_SVM |
3831 CPUID_EXT3_LAHF_LM,
3832 .features[FEAT_SVM] =
3833 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
3834 /* no xsaveopt! */
3835 .xlevel = 0x8000001A,
3836 .model_id = "AMD Opteron 62xx class CPU",
3839 .name = "Opteron_G5",
3840 .level = 0xd,
3841 .vendor = CPUID_VENDOR_AMD,
3842 .family = 21,
3843 .model = 2,
3844 .stepping = 0,
3845 .features[FEAT_1_EDX] =
3846 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3847 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3848 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3849 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3850 CPUID_DE | CPUID_FP87,
3851 .features[FEAT_1_ECX] =
3852 CPUID_EXT_F16C | CPUID_EXT_AVX | CPUID_EXT_XSAVE |
3853 CPUID_EXT_AES | CPUID_EXT_POPCNT | CPUID_EXT_SSE42 |
3854 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_FMA |
3855 CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3,
3856 .features[FEAT_8000_0001_EDX] =
3857 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_NX |
3858 CPUID_EXT2_SYSCALL | CPUID_EXT2_RDTSCP,
3859 .features[FEAT_8000_0001_ECX] =
3860 CPUID_EXT3_TBM | CPUID_EXT3_FMA4 | CPUID_EXT3_XOP |
3861 CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_MISALIGNSSE |
3862 CPUID_EXT3_SSE4A | CPUID_EXT3_ABM | CPUID_EXT3_SVM |
3863 CPUID_EXT3_LAHF_LM,
3864 .features[FEAT_SVM] =
3865 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
3866 /* no xsaveopt! */
3867 .xlevel = 0x8000001A,
3868 .model_id = "AMD Opteron 63xx class CPU",
3871 .name = "EPYC",
3872 .level = 0xd,
3873 .vendor = CPUID_VENDOR_AMD,
3874 .family = 23,
3875 .model = 1,
3876 .stepping = 2,
3877 .features[FEAT_1_EDX] =
3878 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
3879 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
3880 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
3881 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
3882 CPUID_VME | CPUID_FP87,
3883 .features[FEAT_1_ECX] =
3884 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
3885 CPUID_EXT_XSAVE | CPUID_EXT_AES | CPUID_EXT_POPCNT |
3886 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
3887 CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 |
3888 CPUID_EXT_MONITOR | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3,
3889 .features[FEAT_8000_0001_EDX] =
3890 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
3891 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
3892 CPUID_EXT2_SYSCALL,
3893 .features[FEAT_8000_0001_ECX] =
3894 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
3895 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
3896 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
3897 CPUID_EXT3_TOPOEXT,
3898 .features[FEAT_7_0_EBX] =
3899 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
3900 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_RDSEED |
3901 CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT |
3902 CPUID_7_0_EBX_SHA_NI,
3903 .features[FEAT_XSAVE] =
3904 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3905 CPUID_XSAVE_XGETBV1,
3906 .features[FEAT_6_EAX] =
3907 CPUID_6_EAX_ARAT,
3908 .features[FEAT_SVM] =
3909 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
3910 .xlevel = 0x8000001E,
3911 .model_id = "AMD EPYC Processor",
3912 .cache_info = &epyc_cache_info,
3913 .versions = (X86CPUVersionDefinition[]) {
3914 { .version = 1 },
3916 .version = 2,
3917 .alias = "EPYC-IBPB",
3918 .props = (PropValue[]) {
3919 { "ibpb", "on" },
3920 { "model-id",
3921 "AMD EPYC Processor (with IBPB)" },
3922 { /* end of list */ }
3926 .version = 3,
3927 .props = (PropValue[]) {
3928 { "ibpb", "on" },
3929 { "perfctr-core", "on" },
3930 { "clzero", "on" },
3931 { "xsaveerptr", "on" },
3932 { "xsaves", "on" },
3933 { "model-id",
3934 "AMD EPYC Processor" },
3935 { /* end of list */ }
3938 { /* end of list */ }
3942 .name = "Dhyana",
3943 .level = 0xd,
3944 .vendor = CPUID_VENDOR_HYGON,
3945 .family = 24,
3946 .model = 0,
3947 .stepping = 1,
3948 .features[FEAT_1_EDX] =
3949 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
3950 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
3951 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
3952 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
3953 CPUID_VME | CPUID_FP87,
3954 .features[FEAT_1_ECX] =
3955 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
3956 CPUID_EXT_XSAVE | CPUID_EXT_POPCNT |
3957 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
3958 CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 |
3959 CPUID_EXT_MONITOR | CPUID_EXT_SSE3,
3960 .features[FEAT_8000_0001_EDX] =
3961 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
3962 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
3963 CPUID_EXT2_SYSCALL,
3964 .features[FEAT_8000_0001_ECX] =
3965 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
3966 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
3967 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
3968 CPUID_EXT3_TOPOEXT,
3969 .features[FEAT_8000_0008_EBX] =
3970 CPUID_8000_0008_EBX_IBPB,
3971 .features[FEAT_7_0_EBX] =
3972 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
3973 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_RDSEED |
3974 CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT,
3975 /* XSAVES is added in version 2 */
3976 .features[FEAT_XSAVE] =
3977 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3978 CPUID_XSAVE_XGETBV1,
3979 .features[FEAT_6_EAX] =
3980 CPUID_6_EAX_ARAT,
3981 .features[FEAT_SVM] =
3982 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
3983 .xlevel = 0x8000001E,
3984 .model_id = "Hygon Dhyana Processor",
3985 .cache_info = &epyc_cache_info,
3986 .versions = (X86CPUVersionDefinition[]) {
3987 { .version = 1 },
3988 { .version = 2,
3989 .note = "XSAVES",
3990 .props = (PropValue[]) {
3991 { "xsaves", "on" },
3992 { /* end of list */ }
3995 { /* end of list */ }
3999 .name = "EPYC-Rome",
4000 .level = 0xd,
4001 .vendor = CPUID_VENDOR_AMD,
4002 .family = 23,
4003 .model = 49,
4004 .stepping = 0,
4005 .features[FEAT_1_EDX] =
4006 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
4007 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
4008 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
4009 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
4010 CPUID_VME | CPUID_FP87,
4011 .features[FEAT_1_ECX] =
4012 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
4013 CPUID_EXT_XSAVE | CPUID_EXT_AES | CPUID_EXT_POPCNT |
4014 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
4015 CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 |
4016 CPUID_EXT_MONITOR | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3,
4017 .features[FEAT_8000_0001_EDX] =
4018 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
4019 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
4020 CPUID_EXT2_SYSCALL,
4021 .features[FEAT_8000_0001_ECX] =
4022 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
4023 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
4024 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
4025 CPUID_EXT3_TOPOEXT | CPUID_EXT3_PERFCORE,
4026 .features[FEAT_8000_0008_EBX] =
4027 CPUID_8000_0008_EBX_CLZERO | CPUID_8000_0008_EBX_XSAVEERPTR |
4028 CPUID_8000_0008_EBX_WBNOINVD | CPUID_8000_0008_EBX_IBPB |
4029 CPUID_8000_0008_EBX_STIBP,
4030 .features[FEAT_7_0_EBX] =
4031 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
4032 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_RDSEED |
4033 CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT |
4034 CPUID_7_0_EBX_SHA_NI | CPUID_7_0_EBX_CLWB,
4035 .features[FEAT_7_0_ECX] =
4036 CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_RDPID,
4037 .features[FEAT_XSAVE] =
4038 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
4039 CPUID_XSAVE_XGETBV1 | CPUID_XSAVE_XSAVES,
4040 .features[FEAT_6_EAX] =
4041 CPUID_6_EAX_ARAT,
4042 .features[FEAT_SVM] =
4043 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
4044 .xlevel = 0x8000001E,
4045 .model_id = "AMD EPYC-Rome Processor",
4046 .cache_info = &epyc_rome_cache_info,
4047 .versions = (X86CPUVersionDefinition[]) {
4048 { .version = 1 },
4050 .version = 2,
4051 .props = (PropValue[]) {
4052 { "ibrs", "on" },
4053 { "amd-ssbd", "on" },
4054 { /* end of list */ }
4057 { /* end of list */ }
4061 .name = "EPYC-Milan",
4062 .level = 0xd,
4063 .vendor = CPUID_VENDOR_AMD,
4064 .family = 25,
4065 .model = 1,
4066 .stepping = 1,
4067 .features[FEAT_1_EDX] =
4068 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
4069 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
4070 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
4071 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
4072 CPUID_VME | CPUID_FP87,
4073 .features[FEAT_1_ECX] =
4074 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
4075 CPUID_EXT_XSAVE | CPUID_EXT_AES | CPUID_EXT_POPCNT |
4076 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
4077 CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 |
4078 CPUID_EXT_MONITOR | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
4079 CPUID_EXT_PCID,
4080 .features[FEAT_8000_0001_EDX] =
4081 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
4082 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
4083 CPUID_EXT2_SYSCALL,
4084 .features[FEAT_8000_0001_ECX] =
4085 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
4086 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
4087 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
4088 CPUID_EXT3_TOPOEXT | CPUID_EXT3_PERFCORE,
4089 .features[FEAT_8000_0008_EBX] =
4090 CPUID_8000_0008_EBX_CLZERO | CPUID_8000_0008_EBX_XSAVEERPTR |
4091 CPUID_8000_0008_EBX_WBNOINVD | CPUID_8000_0008_EBX_IBPB |
4092 CPUID_8000_0008_EBX_IBRS | CPUID_8000_0008_EBX_STIBP |
4093 CPUID_8000_0008_EBX_AMD_SSBD,
4094 .features[FEAT_7_0_EBX] =
4095 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
4096 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_RDSEED |
4097 CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT |
4098 CPUID_7_0_EBX_SHA_NI | CPUID_7_0_EBX_CLWB | CPUID_7_0_EBX_ERMS |
4099 CPUID_7_0_EBX_INVPCID,
4100 .features[FEAT_7_0_ECX] =
4101 CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_RDPID | CPUID_7_0_ECX_PKU,
4102 .features[FEAT_7_0_EDX] =
4103 CPUID_7_0_EDX_FSRM,
4104 .features[FEAT_XSAVE] =
4105 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
4106 CPUID_XSAVE_XGETBV1 | CPUID_XSAVE_XSAVES,
4107 .features[FEAT_6_EAX] =
4108 CPUID_6_EAX_ARAT,
4109 .features[FEAT_SVM] =
4110 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE | CPUID_SVM_SVME_ADDR_CHK,
4111 .xlevel = 0x8000001E,
4112 .model_id = "AMD EPYC-Milan Processor",
4113 .cache_info = &epyc_milan_cache_info,
4118 * We resolve CPU model aliases using -v1 when using "-machine
4119 * none", but this is just for compatibility while libvirt isn't
4120 * adapted to resolve CPU model versions before creating VMs.
4121 * See "Runnability guarantee of CPU models" at
4122 * docs/about/deprecated.rst.
4124 X86CPUVersion default_cpu_version = 1;
4126 void x86_cpu_set_default_version(X86CPUVersion version)
4128 /* Translating CPU_VERSION_AUTO to CPU_VERSION_AUTO doesn't make sense */
4129 assert(version != CPU_VERSION_AUTO);
4130 default_cpu_version = version;
4133 static X86CPUVersion x86_cpu_model_last_version(const X86CPUModel *model)
4135 int v = 0;
4136 const X86CPUVersionDefinition *vdef =
4137 x86_cpu_def_get_versions(model->cpudef);
4138 while (vdef->version) {
4139 v = vdef->version;
4140 vdef++;
4142 return v;
4145 /* Return the actual version being used for a specific CPU model */
4146 static X86CPUVersion x86_cpu_model_resolve_version(const X86CPUModel *model)
4148 X86CPUVersion v = model->version;
4149 if (v == CPU_VERSION_AUTO) {
4150 v = default_cpu_version;
4152 if (v == CPU_VERSION_LATEST) {
4153 return x86_cpu_model_last_version(model);
4155 return v;
4158 static Property max_x86_cpu_properties[] = {
4159 DEFINE_PROP_BOOL("migratable", X86CPU, migratable, true),
4160 DEFINE_PROP_BOOL("host-cache-info", X86CPU, cache_info_passthrough, false),
4161 DEFINE_PROP_END_OF_LIST()
4164 static void max_x86_cpu_class_init(ObjectClass *oc, void *data)
4166 DeviceClass *dc = DEVICE_CLASS(oc);
4167 X86CPUClass *xcc = X86_CPU_CLASS(oc);
4169 xcc->ordering = 9;
4171 xcc->model_description =
4172 "Enables all features supported by the accelerator in the current host";
4174 device_class_set_props(dc, max_x86_cpu_properties);
4177 static void max_x86_cpu_initfn(Object *obj)
4179 X86CPU *cpu = X86_CPU(obj);
4181 /* We can't fill the features array here because we don't know yet if
4182 * "migratable" is true or false.
4184 cpu->max_features = true;
4185 object_property_set_bool(OBJECT(cpu), "pmu", true, &error_abort);
4188 * these defaults are used for TCG and all other accelerators
4189 * besides KVM and HVF, which overwrite these values
4191 object_property_set_str(OBJECT(cpu), "vendor", CPUID_VENDOR_AMD,
4192 &error_abort);
4193 #ifdef TARGET_X86_64
4194 object_property_set_int(OBJECT(cpu), "family", 15, &error_abort);
4195 object_property_set_int(OBJECT(cpu), "model", 107, &error_abort);
4196 object_property_set_int(OBJECT(cpu), "stepping", 1, &error_abort);
4197 #else
4198 object_property_set_int(OBJECT(cpu), "family", 6, &error_abort);
4199 object_property_set_int(OBJECT(cpu), "model", 6, &error_abort);
4200 object_property_set_int(OBJECT(cpu), "stepping", 3, &error_abort);
4201 #endif
4202 object_property_set_str(OBJECT(cpu), "model-id",
4203 "QEMU TCG CPU version " QEMU_HW_VERSION,
4204 &error_abort);
4207 static const TypeInfo max_x86_cpu_type_info = {
4208 .name = X86_CPU_TYPE_NAME("max"),
4209 .parent = TYPE_X86_CPU,
4210 .instance_init = max_x86_cpu_initfn,
4211 .class_init = max_x86_cpu_class_init,
4214 static char *feature_word_description(FeatureWordInfo *f, uint32_t bit)
4216 assert(f->type == CPUID_FEATURE_WORD || f->type == MSR_FEATURE_WORD);
4218 switch (f->type) {
4219 case CPUID_FEATURE_WORD:
4221 const char *reg = get_register_name_32(f->cpuid.reg);
4222 assert(reg);
4223 return g_strdup_printf("CPUID.%02XH:%s",
4224 f->cpuid.eax, reg);
4226 case MSR_FEATURE_WORD:
4227 return g_strdup_printf("MSR(%02XH)",
4228 f->msr.index);
4231 return NULL;
4234 static bool x86_cpu_have_filtered_features(X86CPU *cpu)
4236 FeatureWord w;
4238 for (w = 0; w < FEATURE_WORDS; w++) {
4239 if (cpu->filtered_features[w]) {
4240 return true;
4244 return false;
4247 static void mark_unavailable_features(X86CPU *cpu, FeatureWord w, uint64_t mask,
4248 const char *verbose_prefix)
4250 CPUX86State *env = &cpu->env;
4251 FeatureWordInfo *f = &feature_word_info[w];
4252 int i;
4254 if (!cpu->force_features) {
4255 env->features[w] &= ~mask;
4257 cpu->filtered_features[w] |= mask;
4259 if (!verbose_prefix) {
4260 return;
4263 for (i = 0; i < 64; ++i) {
4264 if ((1ULL << i) & mask) {
4265 g_autofree char *feat_word_str = feature_word_description(f, i);
4266 warn_report("%s: %s%s%s [bit %d]",
4267 verbose_prefix,
4268 feat_word_str,
4269 f->feat_names[i] ? "." : "",
4270 f->feat_names[i] ? f->feat_names[i] : "", i);
4275 static void x86_cpuid_version_get_family(Object *obj, Visitor *v,
4276 const char *name, void *opaque,
4277 Error **errp)
4279 X86CPU *cpu = X86_CPU(obj);
4280 CPUX86State *env = &cpu->env;
4281 int64_t value;
4283 value = (env->cpuid_version >> 8) & 0xf;
4284 if (value == 0xf) {
4285 value += (env->cpuid_version >> 20) & 0xff;
4287 visit_type_int(v, name, &value, errp);
4290 static void x86_cpuid_version_set_family(Object *obj, Visitor *v,
4291 const char *name, void *opaque,
4292 Error **errp)
4294 X86CPU *cpu = X86_CPU(obj);
4295 CPUX86State *env = &cpu->env;
4296 const int64_t min = 0;
4297 const int64_t max = 0xff + 0xf;
4298 int64_t value;
4300 if (!visit_type_int(v, name, &value, errp)) {
4301 return;
4303 if (value < min || value > max) {
4304 error_setg(errp, QERR_PROPERTY_VALUE_OUT_OF_RANGE, "",
4305 name ? name : "null", value, min, max);
4306 return;
4309 env->cpuid_version &= ~0xff00f00;
4310 if (value > 0x0f) {
4311 env->cpuid_version |= 0xf00 | ((value - 0x0f) << 20);
4312 } else {
4313 env->cpuid_version |= value << 8;
4317 static void x86_cpuid_version_get_model(Object *obj, Visitor *v,
4318 const char *name, void *opaque,
4319 Error **errp)
4321 X86CPU *cpu = X86_CPU(obj);
4322 CPUX86State *env = &cpu->env;
4323 int64_t value;
4325 value = (env->cpuid_version >> 4) & 0xf;
4326 value |= ((env->cpuid_version >> 16) & 0xf) << 4;
4327 visit_type_int(v, name, &value, errp);
4330 static void x86_cpuid_version_set_model(Object *obj, Visitor *v,
4331 const char *name, void *opaque,
4332 Error **errp)
4334 X86CPU *cpu = X86_CPU(obj);
4335 CPUX86State *env = &cpu->env;
4336 const int64_t min = 0;
4337 const int64_t max = 0xff;
4338 int64_t value;
4340 if (!visit_type_int(v, name, &value, errp)) {
4341 return;
4343 if (value < min || value > max) {
4344 error_setg(errp, QERR_PROPERTY_VALUE_OUT_OF_RANGE, "",
4345 name ? name : "null", value, min, max);
4346 return;
4349 env->cpuid_version &= ~0xf00f0;
4350 env->cpuid_version |= ((value & 0xf) << 4) | ((value >> 4) << 16);
4353 static void x86_cpuid_version_get_stepping(Object *obj, Visitor *v,
4354 const char *name, void *opaque,
4355 Error **errp)
4357 X86CPU *cpu = X86_CPU(obj);
4358 CPUX86State *env = &cpu->env;
4359 int64_t value;
4361 value = env->cpuid_version & 0xf;
4362 visit_type_int(v, name, &value, errp);
4365 static void x86_cpuid_version_set_stepping(Object *obj, Visitor *v,
4366 const char *name, void *opaque,
4367 Error **errp)
4369 X86CPU *cpu = X86_CPU(obj);
4370 CPUX86State *env = &cpu->env;
4371 const int64_t min = 0;
4372 const int64_t max = 0xf;
4373 int64_t value;
4375 if (!visit_type_int(v, name, &value, errp)) {
4376 return;
4378 if (value < min || value > max) {
4379 error_setg(errp, QERR_PROPERTY_VALUE_OUT_OF_RANGE, "",
4380 name ? name : "null", value, min, max);
4381 return;
4384 env->cpuid_version &= ~0xf;
4385 env->cpuid_version |= value & 0xf;
4388 static char *x86_cpuid_get_vendor(Object *obj, Error **errp)
4390 X86CPU *cpu = X86_CPU(obj);
4391 CPUX86State *env = &cpu->env;
4392 char *value;
4394 value = g_malloc(CPUID_VENDOR_SZ + 1);
4395 x86_cpu_vendor_words2str(value, env->cpuid_vendor1, env->cpuid_vendor2,
4396 env->cpuid_vendor3);
4397 return value;
4400 static void x86_cpuid_set_vendor(Object *obj, const char *value,
4401 Error **errp)
4403 X86CPU *cpu = X86_CPU(obj);
4404 CPUX86State *env = &cpu->env;
4405 int i;
4407 if (strlen(value) != CPUID_VENDOR_SZ) {
4408 error_setg(errp, QERR_PROPERTY_VALUE_BAD, "", "vendor", value);
4409 return;
4412 env->cpuid_vendor1 = 0;
4413 env->cpuid_vendor2 = 0;
4414 env->cpuid_vendor3 = 0;
4415 for (i = 0; i < 4; i++) {
4416 env->cpuid_vendor1 |= ((uint8_t)value[i ]) << (8 * i);
4417 env->cpuid_vendor2 |= ((uint8_t)value[i + 4]) << (8 * i);
4418 env->cpuid_vendor3 |= ((uint8_t)value[i + 8]) << (8 * i);
4422 static char *x86_cpuid_get_model_id(Object *obj, Error **errp)
4424 X86CPU *cpu = X86_CPU(obj);
4425 CPUX86State *env = &cpu->env;
4426 char *value;
4427 int i;
4429 value = g_malloc(48 + 1);
4430 for (i = 0; i < 48; i++) {
4431 value[i] = env->cpuid_model[i >> 2] >> (8 * (i & 3));
4433 value[48] = '\0';
4434 return value;
4437 static void x86_cpuid_set_model_id(Object *obj, const char *model_id,
4438 Error **errp)
4440 X86CPU *cpu = X86_CPU(obj);
4441 CPUX86State *env = &cpu->env;
4442 int c, len, i;
4444 if (model_id == NULL) {
4445 model_id = "";
4447 len = strlen(model_id);
4448 memset(env->cpuid_model, 0, 48);
4449 for (i = 0; i < 48; i++) {
4450 if (i >= len) {
4451 c = '\0';
4452 } else {
4453 c = (uint8_t)model_id[i];
4455 env->cpuid_model[i >> 2] |= c << (8 * (i & 3));
4459 static void x86_cpuid_get_tsc_freq(Object *obj, Visitor *v, const char *name,
4460 void *opaque, Error **errp)
4462 X86CPU *cpu = X86_CPU(obj);
4463 int64_t value;
4465 value = cpu->env.tsc_khz * 1000;
4466 visit_type_int(v, name, &value, errp);
4469 static void x86_cpuid_set_tsc_freq(Object *obj, Visitor *v, const char *name,
4470 void *opaque, Error **errp)
4472 X86CPU *cpu = X86_CPU(obj);
4473 const int64_t min = 0;
4474 const int64_t max = INT64_MAX;
4475 int64_t value;
4477 if (!visit_type_int(v, name, &value, errp)) {
4478 return;
4480 if (value < min || value > max) {
4481 error_setg(errp, QERR_PROPERTY_VALUE_OUT_OF_RANGE, "",
4482 name ? name : "null", value, min, max);
4483 return;
4486 cpu->env.tsc_khz = cpu->env.user_tsc_khz = value / 1000;
4489 /* Generic getter for "feature-words" and "filtered-features" properties */
4490 static void x86_cpu_get_feature_words(Object *obj, Visitor *v,
4491 const char *name, void *opaque,
4492 Error **errp)
4494 uint64_t *array = (uint64_t *)opaque;
4495 FeatureWord w;
4496 X86CPUFeatureWordInfo word_infos[FEATURE_WORDS] = { };
4497 X86CPUFeatureWordInfoList list_entries[FEATURE_WORDS] = { };
4498 X86CPUFeatureWordInfoList *list = NULL;
4500 for (w = 0; w < FEATURE_WORDS; w++) {
4501 FeatureWordInfo *wi = &feature_word_info[w];
4503 * We didn't have MSR features when "feature-words" was
4504 * introduced. Therefore skipped other type entries.
4506 if (wi->type != CPUID_FEATURE_WORD) {
4507 continue;
4509 X86CPUFeatureWordInfo *qwi = &word_infos[w];
4510 qwi->cpuid_input_eax = wi->cpuid.eax;
4511 qwi->has_cpuid_input_ecx = wi->cpuid.needs_ecx;
4512 qwi->cpuid_input_ecx = wi->cpuid.ecx;
4513 qwi->cpuid_register = x86_reg_info_32[wi->cpuid.reg].qapi_enum;
4514 qwi->features = array[w];
4516 /* List will be in reverse order, but order shouldn't matter */
4517 list_entries[w].next = list;
4518 list_entries[w].value = &word_infos[w];
4519 list = &list_entries[w];
4522 visit_type_X86CPUFeatureWordInfoList(v, "feature-words", &list, errp);
4525 /* Convert all '_' in a feature string option name to '-', to make feature
4526 * name conform to QOM property naming rule, which uses '-' instead of '_'.
4528 static inline void feat2prop(char *s)
4530 while ((s = strchr(s, '_'))) {
4531 *s = '-';
4535 /* Return the feature property name for a feature flag bit */
4536 static const char *x86_cpu_feature_name(FeatureWord w, int bitnr)
4538 const char *name;
4539 /* XSAVE components are automatically enabled by other features,
4540 * so return the original feature name instead
4542 if (w == FEAT_XSAVE_COMP_LO || w == FEAT_XSAVE_COMP_HI) {
4543 int comp = (w == FEAT_XSAVE_COMP_HI) ? bitnr + 32 : bitnr;
4545 if (comp < ARRAY_SIZE(x86_ext_save_areas) &&
4546 x86_ext_save_areas[comp].bits) {
4547 w = x86_ext_save_areas[comp].feature;
4548 bitnr = ctz32(x86_ext_save_areas[comp].bits);
4552 assert(bitnr < 64);
4553 assert(w < FEATURE_WORDS);
4554 name = feature_word_info[w].feat_names[bitnr];
4555 assert(bitnr < 32 || !(name && feature_word_info[w].type == CPUID_FEATURE_WORD));
4556 return name;
4559 /* Compatibily hack to maintain legacy +-feat semantic,
4560 * where +-feat overwrites any feature set by
4561 * feat=on|feat even if the later is parsed after +-feat
4562 * (i.e. "-x2apic,x2apic=on" will result in x2apic disabled)
4564 static GList *plus_features, *minus_features;
4566 static gint compare_string(gconstpointer a, gconstpointer b)
4568 return g_strcmp0(a, b);
4571 /* Parse "+feature,-feature,feature=foo" CPU feature string
4573 static void x86_cpu_parse_featurestr(const char *typename, char *features,
4574 Error **errp)
4576 char *featurestr; /* Single 'key=value" string being parsed */
4577 static bool cpu_globals_initialized;
4578 bool ambiguous = false;
4580 if (cpu_globals_initialized) {
4581 return;
4583 cpu_globals_initialized = true;
4585 if (!features) {
4586 return;
4589 for (featurestr = strtok(features, ",");
4590 featurestr;
4591 featurestr = strtok(NULL, ",")) {
4592 const char *name;
4593 const char *val = NULL;
4594 char *eq = NULL;
4595 char num[32];
4596 GlobalProperty *prop;
4598 /* Compatibility syntax: */
4599 if (featurestr[0] == '+') {
4600 plus_features = g_list_append(plus_features,
4601 g_strdup(featurestr + 1));
4602 continue;
4603 } else if (featurestr[0] == '-') {
4604 minus_features = g_list_append(minus_features,
4605 g_strdup(featurestr + 1));
4606 continue;
4609 eq = strchr(featurestr, '=');
4610 if (eq) {
4611 *eq++ = 0;
4612 val = eq;
4613 } else {
4614 val = "on";
4617 feat2prop(featurestr);
4618 name = featurestr;
4620 if (g_list_find_custom(plus_features, name, compare_string)) {
4621 warn_report("Ambiguous CPU model string. "
4622 "Don't mix both \"+%s\" and \"%s=%s\"",
4623 name, name, val);
4624 ambiguous = true;
4626 if (g_list_find_custom(minus_features, name, compare_string)) {
4627 warn_report("Ambiguous CPU model string. "
4628 "Don't mix both \"-%s\" and \"%s=%s\"",
4629 name, name, val);
4630 ambiguous = true;
4633 /* Special case: */
4634 if (!strcmp(name, "tsc-freq")) {
4635 int ret;
4636 uint64_t tsc_freq;
4638 ret = qemu_strtosz_metric(val, NULL, &tsc_freq);
4639 if (ret < 0 || tsc_freq > INT64_MAX) {
4640 error_setg(errp, "bad numerical value %s", val);
4641 return;
4643 snprintf(num, sizeof(num), "%" PRId64, tsc_freq);
4644 val = num;
4645 name = "tsc-frequency";
4648 prop = g_new0(typeof(*prop), 1);
4649 prop->driver = typename;
4650 prop->property = g_strdup(name);
4651 prop->value = g_strdup(val);
4652 qdev_prop_register_global(prop);
4655 if (ambiguous) {
4656 warn_report("Compatibility of ambiguous CPU model "
4657 "strings won't be kept on future QEMU versions");
4661 static void x86_cpu_filter_features(X86CPU *cpu, bool verbose);
4663 /* Build a list with the name of all features on a feature word array */
4664 static void x86_cpu_list_feature_names(FeatureWordArray features,
4665 strList **list)
4667 strList **tail = list;
4668 FeatureWord w;
4670 for (w = 0; w < FEATURE_WORDS; w++) {
4671 uint64_t filtered = features[w];
4672 int i;
4673 for (i = 0; i < 64; i++) {
4674 if (filtered & (1ULL << i)) {
4675 QAPI_LIST_APPEND(tail, g_strdup(x86_cpu_feature_name(w, i)));
4681 static void x86_cpu_get_unavailable_features(Object *obj, Visitor *v,
4682 const char *name, void *opaque,
4683 Error **errp)
4685 X86CPU *xc = X86_CPU(obj);
4686 strList *result = NULL;
4688 x86_cpu_list_feature_names(xc->filtered_features, &result);
4689 visit_type_strList(v, "unavailable-features", &result, errp);
4692 /* Check for missing features that may prevent the CPU class from
4693 * running using the current machine and accelerator.
4695 static void x86_cpu_class_check_missing_features(X86CPUClass *xcc,
4696 strList **list)
4698 strList **tail = list;
4699 X86CPU *xc;
4700 Error *err = NULL;
4702 if (xcc->host_cpuid_required && !accel_uses_host_cpuid()) {
4703 QAPI_LIST_APPEND(tail, g_strdup("kvm"));
4704 return;
4707 xc = X86_CPU(object_new_with_class(OBJECT_CLASS(xcc)));
4709 x86_cpu_expand_features(xc, &err);
4710 if (err) {
4711 /* Errors at x86_cpu_expand_features should never happen,
4712 * but in case it does, just report the model as not
4713 * runnable at all using the "type" property.
4715 QAPI_LIST_APPEND(tail, g_strdup("type"));
4716 error_free(err);
4719 x86_cpu_filter_features(xc, false);
4721 x86_cpu_list_feature_names(xc->filtered_features, tail);
4723 object_unref(OBJECT(xc));
4726 /* Print all cpuid feature names in featureset
4728 static void listflags(GList *features)
4730 size_t len = 0;
4731 GList *tmp;
4733 for (tmp = features; tmp; tmp = tmp->next) {
4734 const char *name = tmp->data;
4735 if ((len + strlen(name) + 1) >= 75) {
4736 qemu_printf("\n");
4737 len = 0;
4739 qemu_printf("%s%s", len == 0 ? " " : " ", name);
4740 len += strlen(name) + 1;
4742 qemu_printf("\n");
4745 /* Sort alphabetically by type name, respecting X86CPUClass::ordering. */
4746 static gint x86_cpu_list_compare(gconstpointer a, gconstpointer b)
4748 ObjectClass *class_a = (ObjectClass *)a;
4749 ObjectClass *class_b = (ObjectClass *)b;
4750 X86CPUClass *cc_a = X86_CPU_CLASS(class_a);
4751 X86CPUClass *cc_b = X86_CPU_CLASS(class_b);
4752 int ret;
4754 if (cc_a->ordering != cc_b->ordering) {
4755 ret = cc_a->ordering - cc_b->ordering;
4756 } else {
4757 g_autofree char *name_a = x86_cpu_class_get_model_name(cc_a);
4758 g_autofree char *name_b = x86_cpu_class_get_model_name(cc_b);
4759 ret = strcmp(name_a, name_b);
4761 return ret;
4764 static GSList *get_sorted_cpu_model_list(void)
4766 GSList *list = object_class_get_list(TYPE_X86_CPU, false);
4767 list = g_slist_sort(list, x86_cpu_list_compare);
4768 return list;
4771 static char *x86_cpu_class_get_model_id(X86CPUClass *xc)
4773 Object *obj = object_new_with_class(OBJECT_CLASS(xc));
4774 char *r = object_property_get_str(obj, "model-id", &error_abort);
4775 object_unref(obj);
4776 return r;
4779 static char *x86_cpu_class_get_alias_of(X86CPUClass *cc)
4781 X86CPUVersion version;
4783 if (!cc->model || !cc->model->is_alias) {
4784 return NULL;
4786 version = x86_cpu_model_resolve_version(cc->model);
4787 if (version <= 0) {
4788 return NULL;
4790 return x86_cpu_versioned_model_name(cc->model->cpudef, version);
4793 static void x86_cpu_list_entry(gpointer data, gpointer user_data)
4795 ObjectClass *oc = data;
4796 X86CPUClass *cc = X86_CPU_CLASS(oc);
4797 g_autofree char *name = x86_cpu_class_get_model_name(cc);
4798 g_autofree char *desc = g_strdup(cc->model_description);
4799 g_autofree char *alias_of = x86_cpu_class_get_alias_of(cc);
4800 g_autofree char *model_id = x86_cpu_class_get_model_id(cc);
4802 if (!desc && alias_of) {
4803 if (cc->model && cc->model->version == CPU_VERSION_AUTO) {
4804 desc = g_strdup("(alias configured by machine type)");
4805 } else {
4806 desc = g_strdup_printf("(alias of %s)", alias_of);
4809 if (!desc && cc->model && cc->model->note) {
4810 desc = g_strdup_printf("%s [%s]", model_id, cc->model->note);
4812 if (!desc) {
4813 desc = g_strdup_printf("%s", model_id);
4816 qemu_printf("x86 %-20s %-58s\n", name, desc);
4819 /* list available CPU models and flags */
4820 void x86_cpu_list(void)
4822 int i, j;
4823 GSList *list;
4824 GList *names = NULL;
4826 qemu_printf("Available CPUs:\n");
4827 list = get_sorted_cpu_model_list();
4828 g_slist_foreach(list, x86_cpu_list_entry, NULL);
4829 g_slist_free(list);
4831 names = NULL;
4832 for (i = 0; i < ARRAY_SIZE(feature_word_info); i++) {
4833 FeatureWordInfo *fw = &feature_word_info[i];
4834 for (j = 0; j < 64; j++) {
4835 if (fw->feat_names[j]) {
4836 names = g_list_append(names, (gpointer)fw->feat_names[j]);
4841 names = g_list_sort(names, (GCompareFunc)strcmp);
4843 qemu_printf("\nRecognized CPUID flags:\n");
4844 listflags(names);
4845 qemu_printf("\n");
4846 g_list_free(names);
4849 static void x86_cpu_definition_entry(gpointer data, gpointer user_data)
4851 ObjectClass *oc = data;
4852 X86CPUClass *cc = X86_CPU_CLASS(oc);
4853 CpuDefinitionInfoList **cpu_list = user_data;
4854 CpuDefinitionInfo *info;
4856 info = g_malloc0(sizeof(*info));
4857 info->name = x86_cpu_class_get_model_name(cc);
4858 x86_cpu_class_check_missing_features(cc, &info->unavailable_features);
4859 info->has_unavailable_features = true;
4860 info->q_typename = g_strdup(object_class_get_name(oc));
4861 info->migration_safe = cc->migration_safe;
4862 info->has_migration_safe = true;
4863 info->q_static = cc->static_model;
4864 if (cc->model && cc->model->cpudef->deprecation_note) {
4865 info->deprecated = true;
4866 } else {
4867 info->deprecated = false;
4870 * Old machine types won't report aliases, so that alias translation
4871 * doesn't break compatibility with previous QEMU versions.
4873 if (default_cpu_version != CPU_VERSION_LEGACY) {
4874 info->alias_of = x86_cpu_class_get_alias_of(cc);
4875 info->has_alias_of = !!info->alias_of;
4878 QAPI_LIST_PREPEND(*cpu_list, info);
4881 CpuDefinitionInfoList *qmp_query_cpu_definitions(Error **errp)
4883 CpuDefinitionInfoList *cpu_list = NULL;
4884 GSList *list = get_sorted_cpu_model_list();
4885 g_slist_foreach(list, x86_cpu_definition_entry, &cpu_list);
4886 g_slist_free(list);
4887 return cpu_list;
4890 static uint64_t x86_cpu_get_supported_feature_word(FeatureWord w,
4891 bool migratable_only)
4893 FeatureWordInfo *wi = &feature_word_info[w];
4894 uint64_t r = 0;
4896 if (kvm_enabled()) {
4897 switch (wi->type) {
4898 case CPUID_FEATURE_WORD:
4899 r = kvm_arch_get_supported_cpuid(kvm_state, wi->cpuid.eax,
4900 wi->cpuid.ecx,
4901 wi->cpuid.reg);
4902 break;
4903 case MSR_FEATURE_WORD:
4904 r = kvm_arch_get_supported_msr_feature(kvm_state,
4905 wi->msr.index);
4906 break;
4908 } else if (hvf_enabled()) {
4909 if (wi->type != CPUID_FEATURE_WORD) {
4910 return 0;
4912 r = hvf_get_supported_cpuid(wi->cpuid.eax,
4913 wi->cpuid.ecx,
4914 wi->cpuid.reg);
4915 } else if (tcg_enabled()) {
4916 r = wi->tcg_features;
4917 } else {
4918 return ~0;
4920 #ifndef TARGET_X86_64
4921 if (w == FEAT_8000_0001_EDX) {
4922 r &= ~CPUID_EXT2_LM;
4924 #endif
4925 if (migratable_only) {
4926 r &= x86_cpu_get_migratable_flags(w);
4928 return r;
4932 * Only for builtin_x86_defs models initialized with x86_register_cpudef_types.
4934 void x86_cpu_apply_props(X86CPU *cpu, PropValue *props)
4936 PropValue *pv;
4937 for (pv = props; pv->prop; pv++) {
4938 if (!pv->value) {
4939 continue;
4941 object_property_parse(OBJECT(cpu), pv->prop, pv->value,
4942 &error_abort);
4947 * Apply properties for the CPU model version specified in model.
4948 * Only for builtin_x86_defs models initialized with x86_register_cpudef_types.
4951 static void x86_cpu_apply_version_props(X86CPU *cpu, X86CPUModel *model)
4953 const X86CPUVersionDefinition *vdef;
4954 X86CPUVersion version = x86_cpu_model_resolve_version(model);
4956 if (version == CPU_VERSION_LEGACY) {
4957 return;
4960 for (vdef = x86_cpu_def_get_versions(model->cpudef); vdef->version; vdef++) {
4961 PropValue *p;
4963 for (p = vdef->props; p && p->prop; p++) {
4964 object_property_parse(OBJECT(cpu), p->prop, p->value,
4965 &error_abort);
4968 if (vdef->version == version) {
4969 break;
4974 * If we reached the end of the list, version number was invalid
4976 assert(vdef->version == version);
4980 * Load data from X86CPUDefinition into a X86CPU object.
4981 * Only for builtin_x86_defs models initialized with x86_register_cpudef_types.
4983 static void x86_cpu_load_model(X86CPU *cpu, X86CPUModel *model)
4985 const X86CPUDefinition *def = model->cpudef;
4986 CPUX86State *env = &cpu->env;
4987 FeatureWord w;
4989 /*NOTE: any property set by this function should be returned by
4990 * x86_cpu_static_props(), so static expansion of
4991 * query-cpu-model-expansion is always complete.
4994 /* CPU models only set _minimum_ values for level/xlevel: */
4995 object_property_set_uint(OBJECT(cpu), "min-level", def->level,
4996 &error_abort);
4997 object_property_set_uint(OBJECT(cpu), "min-xlevel", def->xlevel,
4998 &error_abort);
5000 object_property_set_int(OBJECT(cpu), "family", def->family, &error_abort);
5001 object_property_set_int(OBJECT(cpu), "model", def->model, &error_abort);
5002 object_property_set_int(OBJECT(cpu), "stepping", def->stepping,
5003 &error_abort);
5004 object_property_set_str(OBJECT(cpu), "model-id", def->model_id,
5005 &error_abort);
5006 for (w = 0; w < FEATURE_WORDS; w++) {
5007 env->features[w] = def->features[w];
5010 /* legacy-cache defaults to 'off' if CPU model provides cache info */
5011 cpu->legacy_cache = !def->cache_info;
5013 env->features[FEAT_1_ECX] |= CPUID_EXT_HYPERVISOR;
5015 /* sysenter isn't supported in compatibility mode on AMD,
5016 * syscall isn't supported in compatibility mode on Intel.
5017 * Normally we advertise the actual CPU vendor, but you can
5018 * override this using the 'vendor' property if you want to use
5019 * KVM's sysenter/syscall emulation in compatibility mode and
5020 * when doing cross vendor migration
5024 * vendor property is set here but then overloaded with the
5025 * host cpu vendor for KVM and HVF.
5027 object_property_set_str(OBJECT(cpu), "vendor", def->vendor, &error_abort);
5029 x86_cpu_apply_version_props(cpu, model);
5032 * Properties in versioned CPU model are not user specified features.
5033 * We can simply clear env->user_features here since it will be filled later
5034 * in x86_cpu_expand_features() based on plus_features and minus_features.
5036 memset(&env->user_features, 0, sizeof(env->user_features));
5039 static gchar *x86_gdb_arch_name(CPUState *cs)
5041 #ifdef TARGET_X86_64
5042 return g_strdup("i386:x86-64");
5043 #else
5044 return g_strdup("i386");
5045 #endif
5048 static void x86_cpu_cpudef_class_init(ObjectClass *oc, void *data)
5050 X86CPUModel *model = data;
5051 X86CPUClass *xcc = X86_CPU_CLASS(oc);
5052 CPUClass *cc = CPU_CLASS(oc);
5054 xcc->model = model;
5055 xcc->migration_safe = true;
5056 cc->deprecation_note = model->cpudef->deprecation_note;
5059 static void x86_register_cpu_model_type(const char *name, X86CPUModel *model)
5061 g_autofree char *typename = x86_cpu_type_name(name);
5062 TypeInfo ti = {
5063 .name = typename,
5064 .parent = TYPE_X86_CPU,
5065 .class_init = x86_cpu_cpudef_class_init,
5066 .class_data = model,
5069 type_register(&ti);
5074 * register builtin_x86_defs;
5075 * "max", "base" and subclasses ("host") are not registered here.
5076 * See x86_cpu_register_types for all model registrations.
5078 static void x86_register_cpudef_types(const X86CPUDefinition *def)
5080 X86CPUModel *m;
5081 const X86CPUVersionDefinition *vdef;
5083 /* AMD aliases are handled at runtime based on CPUID vendor, so
5084 * they shouldn't be set on the CPU model table.
5086 assert(!(def->features[FEAT_8000_0001_EDX] & CPUID_EXT2_AMD_ALIASES));
5087 /* catch mistakes instead of silently truncating model_id when too long */
5088 assert(def->model_id && strlen(def->model_id) <= 48);
5090 /* Unversioned model: */
5091 m = g_new0(X86CPUModel, 1);
5092 m->cpudef = def;
5093 m->version = CPU_VERSION_AUTO;
5094 m->is_alias = true;
5095 x86_register_cpu_model_type(def->name, m);
5097 /* Versioned models: */
5099 for (vdef = x86_cpu_def_get_versions(def); vdef->version; vdef++) {
5100 X86CPUModel *m = g_new0(X86CPUModel, 1);
5101 g_autofree char *name =
5102 x86_cpu_versioned_model_name(def, vdef->version);
5103 m->cpudef = def;
5104 m->version = vdef->version;
5105 m->note = vdef->note;
5106 x86_register_cpu_model_type(name, m);
5108 if (vdef->alias) {
5109 X86CPUModel *am = g_new0(X86CPUModel, 1);
5110 am->cpudef = def;
5111 am->version = vdef->version;
5112 am->is_alias = true;
5113 x86_register_cpu_model_type(vdef->alias, am);
5119 uint32_t cpu_x86_virtual_addr_width(CPUX86State *env)
5121 if (env->features[FEAT_7_0_ECX] & CPUID_7_0_ECX_LA57) {
5122 return 57; /* 57 bits virtual */
5123 } else {
5124 return 48; /* 48 bits virtual */
5128 void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count,
5129 uint32_t *eax, uint32_t *ebx,
5130 uint32_t *ecx, uint32_t *edx)
5132 X86CPU *cpu = env_archcpu(env);
5133 CPUState *cs = env_cpu(env);
5134 uint32_t die_offset;
5135 uint32_t limit;
5136 uint32_t signature[3];
5137 X86CPUTopoInfo topo_info;
5139 topo_info.dies_per_pkg = env->nr_dies;
5140 topo_info.cores_per_die = cs->nr_cores;
5141 topo_info.threads_per_core = cs->nr_threads;
5143 /* Calculate & apply limits for different index ranges */
5144 if (index >= 0xC0000000) {
5145 limit = env->cpuid_xlevel2;
5146 } else if (index >= 0x80000000) {
5147 limit = env->cpuid_xlevel;
5148 } else if (index >= 0x40000000) {
5149 limit = 0x40000001;
5150 } else {
5151 limit = env->cpuid_level;
5154 if (index > limit) {
5155 /* Intel documentation states that invalid EAX input will
5156 * return the same information as EAX=cpuid_level
5157 * (Intel SDM Vol. 2A - Instruction Set Reference - CPUID)
5159 index = env->cpuid_level;
5162 switch(index) {
5163 case 0:
5164 *eax = env->cpuid_level;
5165 *ebx = env->cpuid_vendor1;
5166 *edx = env->cpuid_vendor2;
5167 *ecx = env->cpuid_vendor3;
5168 break;
5169 case 1:
5170 *eax = env->cpuid_version;
5171 *ebx = (cpu->apic_id << 24) |
5172 8 << 8; /* CLFLUSH size in quad words, Linux wants it. */
5173 *ecx = env->features[FEAT_1_ECX];
5174 if ((*ecx & CPUID_EXT_XSAVE) && (env->cr[4] & CR4_OSXSAVE_MASK)) {
5175 *ecx |= CPUID_EXT_OSXSAVE;
5177 *edx = env->features[FEAT_1_EDX];
5178 if (cs->nr_cores * cs->nr_threads > 1) {
5179 *ebx |= (cs->nr_cores * cs->nr_threads) << 16;
5180 *edx |= CPUID_HT;
5182 if (!cpu->enable_pmu) {
5183 *ecx &= ~CPUID_EXT_PDCM;
5185 break;
5186 case 2:
5187 /* cache info: needed for Pentium Pro compatibility */
5188 if (cpu->cache_info_passthrough) {
5189 host_cpuid(index, 0, eax, ebx, ecx, edx);
5190 break;
5191 } else if (cpu->vendor_cpuid_only && IS_AMD_CPU(env)) {
5192 *eax = *ebx = *ecx = *edx = 0;
5193 break;
5195 *eax = 1; /* Number of CPUID[EAX=2] calls required */
5196 *ebx = 0;
5197 if (!cpu->enable_l3_cache) {
5198 *ecx = 0;
5199 } else {
5200 *ecx = cpuid2_cache_descriptor(env->cache_info_cpuid2.l3_cache);
5202 *edx = (cpuid2_cache_descriptor(env->cache_info_cpuid2.l1d_cache) << 16) |
5203 (cpuid2_cache_descriptor(env->cache_info_cpuid2.l1i_cache) << 8) |
5204 (cpuid2_cache_descriptor(env->cache_info_cpuid2.l2_cache));
5205 break;
5206 case 4:
5207 /* cache info: needed for Core compatibility */
5208 if (cpu->cache_info_passthrough) {
5209 host_cpuid(index, count, eax, ebx, ecx, edx);
5210 /* QEMU gives out its own APIC IDs, never pass down bits 31..26. */
5211 *eax &= ~0xFC000000;
5212 if ((*eax & 31) && cs->nr_cores > 1) {
5213 *eax |= (cs->nr_cores - 1) << 26;
5215 } else if (cpu->vendor_cpuid_only && IS_AMD_CPU(env)) {
5216 *eax = *ebx = *ecx = *edx = 0;
5217 } else {
5218 *eax = 0;
5219 switch (count) {
5220 case 0: /* L1 dcache info */
5221 encode_cache_cpuid4(env->cache_info_cpuid4.l1d_cache,
5222 1, cs->nr_cores,
5223 eax, ebx, ecx, edx);
5224 break;
5225 case 1: /* L1 icache info */
5226 encode_cache_cpuid4(env->cache_info_cpuid4.l1i_cache,
5227 1, cs->nr_cores,
5228 eax, ebx, ecx, edx);
5229 break;
5230 case 2: /* L2 cache info */
5231 encode_cache_cpuid4(env->cache_info_cpuid4.l2_cache,
5232 cs->nr_threads, cs->nr_cores,
5233 eax, ebx, ecx, edx);
5234 break;
5235 case 3: /* L3 cache info */
5236 die_offset = apicid_die_offset(&topo_info);
5237 if (cpu->enable_l3_cache) {
5238 encode_cache_cpuid4(env->cache_info_cpuid4.l3_cache,
5239 (1 << die_offset), cs->nr_cores,
5240 eax, ebx, ecx, edx);
5241 break;
5243 /* fall through */
5244 default: /* end of info */
5245 *eax = *ebx = *ecx = *edx = 0;
5246 break;
5249 break;
5250 case 5:
5251 /* MONITOR/MWAIT Leaf */
5252 *eax = cpu->mwait.eax; /* Smallest monitor-line size in bytes */
5253 *ebx = cpu->mwait.ebx; /* Largest monitor-line size in bytes */
5254 *ecx = cpu->mwait.ecx; /* flags */
5255 *edx = cpu->mwait.edx; /* mwait substates */
5256 break;
5257 case 6:
5258 /* Thermal and Power Leaf */
5259 *eax = env->features[FEAT_6_EAX];
5260 *ebx = 0;
5261 *ecx = 0;
5262 *edx = 0;
5263 break;
5264 case 7:
5265 /* Structured Extended Feature Flags Enumeration Leaf */
5266 if (count == 0) {
5267 /* Maximum ECX value for sub-leaves */
5268 *eax = env->cpuid_level_func7;
5269 *ebx = env->features[FEAT_7_0_EBX]; /* Feature flags */
5270 *ecx = env->features[FEAT_7_0_ECX]; /* Feature flags */
5271 if ((*ecx & CPUID_7_0_ECX_PKU) && env->cr[4] & CR4_PKE_MASK) {
5272 *ecx |= CPUID_7_0_ECX_OSPKE;
5274 *edx = env->features[FEAT_7_0_EDX]; /* Feature flags */
5275 } else if (count == 1) {
5276 *eax = env->features[FEAT_7_1_EAX];
5277 *ebx = 0;
5278 *ecx = 0;
5279 *edx = 0;
5280 } else {
5281 *eax = 0;
5282 *ebx = 0;
5283 *ecx = 0;
5284 *edx = 0;
5286 break;
5287 case 9:
5288 /* Direct Cache Access Information Leaf */
5289 *eax = 0; /* Bits 0-31 in DCA_CAP MSR */
5290 *ebx = 0;
5291 *ecx = 0;
5292 *edx = 0;
5293 break;
5294 case 0xA:
5295 /* Architectural Performance Monitoring Leaf */
5296 if (kvm_enabled() && cpu->enable_pmu) {
5297 KVMState *s = cs->kvm_state;
5299 *eax = kvm_arch_get_supported_cpuid(s, 0xA, count, R_EAX);
5300 *ebx = kvm_arch_get_supported_cpuid(s, 0xA, count, R_EBX);
5301 *ecx = kvm_arch_get_supported_cpuid(s, 0xA, count, R_ECX);
5302 *edx = kvm_arch_get_supported_cpuid(s, 0xA, count, R_EDX);
5303 } else if (hvf_enabled() && cpu->enable_pmu) {
5304 *eax = hvf_get_supported_cpuid(0xA, count, R_EAX);
5305 *ebx = hvf_get_supported_cpuid(0xA, count, R_EBX);
5306 *ecx = hvf_get_supported_cpuid(0xA, count, R_ECX);
5307 *edx = hvf_get_supported_cpuid(0xA, count, R_EDX);
5308 } else {
5309 *eax = 0;
5310 *ebx = 0;
5311 *ecx = 0;
5312 *edx = 0;
5314 break;
5315 case 0xB:
5316 /* Extended Topology Enumeration Leaf */
5317 if (!cpu->enable_cpuid_0xb) {
5318 *eax = *ebx = *ecx = *edx = 0;
5319 break;
5322 *ecx = count & 0xff;
5323 *edx = cpu->apic_id;
5325 switch (count) {
5326 case 0:
5327 *eax = apicid_core_offset(&topo_info);
5328 *ebx = cs->nr_threads;
5329 *ecx |= CPUID_TOPOLOGY_LEVEL_SMT;
5330 break;
5331 case 1:
5332 *eax = apicid_pkg_offset(&topo_info);
5333 *ebx = cs->nr_cores * cs->nr_threads;
5334 *ecx |= CPUID_TOPOLOGY_LEVEL_CORE;
5335 break;
5336 default:
5337 *eax = 0;
5338 *ebx = 0;
5339 *ecx |= CPUID_TOPOLOGY_LEVEL_INVALID;
5342 assert(!(*eax & ~0x1f));
5343 *ebx &= 0xffff; /* The count doesn't need to be reliable. */
5344 break;
5345 case 0x1F:
5346 /* V2 Extended Topology Enumeration Leaf */
5347 if (env->nr_dies < 2) {
5348 *eax = *ebx = *ecx = *edx = 0;
5349 break;
5352 *ecx = count & 0xff;
5353 *edx = cpu->apic_id;
5354 switch (count) {
5355 case 0:
5356 *eax = apicid_core_offset(&topo_info);
5357 *ebx = cs->nr_threads;
5358 *ecx |= CPUID_TOPOLOGY_LEVEL_SMT;
5359 break;
5360 case 1:
5361 *eax = apicid_die_offset(&topo_info);
5362 *ebx = cs->nr_cores * cs->nr_threads;
5363 *ecx |= CPUID_TOPOLOGY_LEVEL_CORE;
5364 break;
5365 case 2:
5366 *eax = apicid_pkg_offset(&topo_info);
5367 *ebx = env->nr_dies * cs->nr_cores * cs->nr_threads;
5368 *ecx |= CPUID_TOPOLOGY_LEVEL_DIE;
5369 break;
5370 default:
5371 *eax = 0;
5372 *ebx = 0;
5373 *ecx |= CPUID_TOPOLOGY_LEVEL_INVALID;
5375 assert(!(*eax & ~0x1f));
5376 *ebx &= 0xffff; /* The count doesn't need to be reliable. */
5377 break;
5378 case 0xD: {
5379 /* Processor Extended State */
5380 *eax = 0;
5381 *ebx = 0;
5382 *ecx = 0;
5383 *edx = 0;
5384 if (!(env->features[FEAT_1_ECX] & CPUID_EXT_XSAVE)) {
5385 break;
5388 if (count == 0) {
5389 *ecx = xsave_area_size(x86_cpu_xsave_components(cpu));
5390 *eax = env->features[FEAT_XSAVE_COMP_LO];
5391 *edx = env->features[FEAT_XSAVE_COMP_HI];
5393 * The initial value of xcr0 and ebx == 0, On host without kvm
5394 * commit 412a3c41(e.g., CentOS 6), the ebx's value always == 0
5395 * even through guest update xcr0, this will crash some legacy guest
5396 * (e.g., CentOS 6), So set ebx == ecx to workaroud it.
5398 *ebx = kvm_enabled() ? *ecx : xsave_area_size(env->xcr0);
5399 } else if (count == 1) {
5400 *eax = env->features[FEAT_XSAVE];
5401 } else if (count < ARRAY_SIZE(x86_ext_save_areas)) {
5402 if ((x86_cpu_xsave_components(cpu) >> count) & 1) {
5403 const ExtSaveArea *esa = &x86_ext_save_areas[count];
5404 *eax = esa->size;
5405 *ebx = esa->offset;
5408 break;
5410 case 0x14: {
5411 /* Intel Processor Trace Enumeration */
5412 *eax = 0;
5413 *ebx = 0;
5414 *ecx = 0;
5415 *edx = 0;
5416 if (!(env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_INTEL_PT) ||
5417 !kvm_enabled()) {
5418 break;
5421 if (count == 0) {
5422 *eax = INTEL_PT_MAX_SUBLEAF;
5423 *ebx = INTEL_PT_MINIMAL_EBX;
5424 *ecx = INTEL_PT_MINIMAL_ECX;
5425 if (env->features[FEAT_14_0_ECX] & CPUID_14_0_ECX_LIP) {
5426 *ecx |= CPUID_14_0_ECX_LIP;
5428 } else if (count == 1) {
5429 *eax = INTEL_PT_MTC_BITMAP | INTEL_PT_ADDR_RANGES_NUM;
5430 *ebx = INTEL_PT_PSB_BITMAP | INTEL_PT_CYCLE_BITMAP;
5432 break;
5434 case 0x40000000:
5436 * CPUID code in kvm_arch_init_vcpu() ignores stuff
5437 * set here, but we restrict to TCG none the less.
5439 if (tcg_enabled() && cpu->expose_tcg) {
5440 memcpy(signature, "TCGTCGTCGTCG", 12);
5441 *eax = 0x40000001;
5442 *ebx = signature[0];
5443 *ecx = signature[1];
5444 *edx = signature[2];
5445 } else {
5446 *eax = 0;
5447 *ebx = 0;
5448 *ecx = 0;
5449 *edx = 0;
5451 break;
5452 case 0x40000001:
5453 *eax = 0;
5454 *ebx = 0;
5455 *ecx = 0;
5456 *edx = 0;
5457 break;
5458 case 0x80000000:
5459 *eax = env->cpuid_xlevel;
5460 *ebx = env->cpuid_vendor1;
5461 *edx = env->cpuid_vendor2;
5462 *ecx = env->cpuid_vendor3;
5463 break;
5464 case 0x80000001:
5465 *eax = env->cpuid_version;
5466 *ebx = 0;
5467 *ecx = env->features[FEAT_8000_0001_ECX];
5468 *edx = env->features[FEAT_8000_0001_EDX];
5470 /* The Linux kernel checks for the CMPLegacy bit and
5471 * discards multiple thread information if it is set.
5472 * So don't set it here for Intel to make Linux guests happy.
5474 if (cs->nr_cores * cs->nr_threads > 1) {
5475 if (env->cpuid_vendor1 != CPUID_VENDOR_INTEL_1 ||
5476 env->cpuid_vendor2 != CPUID_VENDOR_INTEL_2 ||
5477 env->cpuid_vendor3 != CPUID_VENDOR_INTEL_3) {
5478 *ecx |= 1 << 1; /* CmpLegacy bit */
5481 break;
5482 case 0x80000002:
5483 case 0x80000003:
5484 case 0x80000004:
5485 *eax = env->cpuid_model[(index - 0x80000002) * 4 + 0];
5486 *ebx = env->cpuid_model[(index - 0x80000002) * 4 + 1];
5487 *ecx = env->cpuid_model[(index - 0x80000002) * 4 + 2];
5488 *edx = env->cpuid_model[(index - 0x80000002) * 4 + 3];
5489 break;
5490 case 0x80000005:
5491 /* cache info (L1 cache) */
5492 if (cpu->cache_info_passthrough) {
5493 host_cpuid(index, 0, eax, ebx, ecx, edx);
5494 break;
5496 *eax = (L1_DTLB_2M_ASSOC << 24) | (L1_DTLB_2M_ENTRIES << 16) |
5497 (L1_ITLB_2M_ASSOC << 8) | (L1_ITLB_2M_ENTRIES);
5498 *ebx = (L1_DTLB_4K_ASSOC << 24) | (L1_DTLB_4K_ENTRIES << 16) |
5499 (L1_ITLB_4K_ASSOC << 8) | (L1_ITLB_4K_ENTRIES);
5500 *ecx = encode_cache_cpuid80000005(env->cache_info_amd.l1d_cache);
5501 *edx = encode_cache_cpuid80000005(env->cache_info_amd.l1i_cache);
5502 break;
5503 case 0x80000006:
5504 /* cache info (L2 cache) */
5505 if (cpu->cache_info_passthrough) {
5506 host_cpuid(index, 0, eax, ebx, ecx, edx);
5507 break;
5509 *eax = (AMD_ENC_ASSOC(L2_DTLB_2M_ASSOC) << 28) |
5510 (L2_DTLB_2M_ENTRIES << 16) |
5511 (AMD_ENC_ASSOC(L2_ITLB_2M_ASSOC) << 12) |
5512 (L2_ITLB_2M_ENTRIES);
5513 *ebx = (AMD_ENC_ASSOC(L2_DTLB_4K_ASSOC) << 28) |
5514 (L2_DTLB_4K_ENTRIES << 16) |
5515 (AMD_ENC_ASSOC(L2_ITLB_4K_ASSOC) << 12) |
5516 (L2_ITLB_4K_ENTRIES);
5517 encode_cache_cpuid80000006(env->cache_info_amd.l2_cache,
5518 cpu->enable_l3_cache ?
5519 env->cache_info_amd.l3_cache : NULL,
5520 ecx, edx);
5521 break;
5522 case 0x80000007:
5523 *eax = 0;
5524 *ebx = 0;
5525 *ecx = 0;
5526 *edx = env->features[FEAT_8000_0007_EDX];
5527 break;
5528 case 0x80000008:
5529 /* virtual & phys address size in low 2 bytes. */
5530 *eax = cpu->phys_bits;
5531 if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_LM) {
5532 /* 64 bit processor */
5533 *eax |= (cpu_x86_virtual_addr_width(env) << 8);
5535 *ebx = env->features[FEAT_8000_0008_EBX];
5536 if (cs->nr_cores * cs->nr_threads > 1) {
5538 * Bits 15:12 is "The number of bits in the initial
5539 * Core::X86::Apic::ApicId[ApicId] value that indicate
5540 * thread ID within a package".
5541 * Bits 7:0 is "The number of threads in the package is NC+1"
5543 *ecx = (apicid_pkg_offset(&topo_info) << 12) |
5544 ((cs->nr_cores * cs->nr_threads) - 1);
5545 } else {
5546 *ecx = 0;
5548 *edx = 0;
5549 break;
5550 case 0x8000000A:
5551 if (env->features[FEAT_8000_0001_ECX] & CPUID_EXT3_SVM) {
5552 *eax = 0x00000001; /* SVM Revision */
5553 *ebx = 0x00000010; /* nr of ASIDs */
5554 *ecx = 0;
5555 *edx = env->features[FEAT_SVM]; /* optional features */
5556 } else {
5557 *eax = 0;
5558 *ebx = 0;
5559 *ecx = 0;
5560 *edx = 0;
5562 break;
5563 case 0x8000001D:
5564 *eax = 0;
5565 if (cpu->cache_info_passthrough) {
5566 host_cpuid(index, count, eax, ebx, ecx, edx);
5567 break;
5569 switch (count) {
5570 case 0: /* L1 dcache info */
5571 encode_cache_cpuid8000001d(env->cache_info_amd.l1d_cache,
5572 &topo_info, eax, ebx, ecx, edx);
5573 break;
5574 case 1: /* L1 icache info */
5575 encode_cache_cpuid8000001d(env->cache_info_amd.l1i_cache,
5576 &topo_info, eax, ebx, ecx, edx);
5577 break;
5578 case 2: /* L2 cache info */
5579 encode_cache_cpuid8000001d(env->cache_info_amd.l2_cache,
5580 &topo_info, eax, ebx, ecx, edx);
5581 break;
5582 case 3: /* L3 cache info */
5583 encode_cache_cpuid8000001d(env->cache_info_amd.l3_cache,
5584 &topo_info, eax, ebx, ecx, edx);
5585 break;
5586 default: /* end of info */
5587 *eax = *ebx = *ecx = *edx = 0;
5588 break;
5590 break;
5591 case 0x8000001E:
5592 if (cpu->core_id <= 255) {
5593 encode_topo_cpuid8000001e(cpu, &topo_info, eax, ebx, ecx, edx);
5594 } else {
5595 *eax = 0;
5596 *ebx = 0;
5597 *ecx = 0;
5598 *edx = 0;
5600 break;
5601 case 0xC0000000:
5602 *eax = env->cpuid_xlevel2;
5603 *ebx = 0;
5604 *ecx = 0;
5605 *edx = 0;
5606 break;
5607 case 0xC0000001:
5608 /* Support for VIA CPU's CPUID instruction */
5609 *eax = env->cpuid_version;
5610 *ebx = 0;
5611 *ecx = 0;
5612 *edx = env->features[FEAT_C000_0001_EDX];
5613 break;
5614 case 0xC0000002:
5615 case 0xC0000003:
5616 case 0xC0000004:
5617 /* Reserved for the future, and now filled with zero */
5618 *eax = 0;
5619 *ebx = 0;
5620 *ecx = 0;
5621 *edx = 0;
5622 break;
5623 case 0x8000001F:
5624 *eax = sev_enabled() ? 0x2 : 0;
5625 *eax |= sev_es_enabled() ? 0x8 : 0;
5626 *ebx = sev_get_cbit_position();
5627 *ebx |= sev_get_reduced_phys_bits() << 6;
5628 *ecx = 0;
5629 *edx = 0;
5630 break;
5631 default:
5632 /* reserved values: zero */
5633 *eax = 0;
5634 *ebx = 0;
5635 *ecx = 0;
5636 *edx = 0;
5637 break;
5641 static void x86_cpu_reset(DeviceState *dev)
5643 CPUState *s = CPU(dev);
5644 X86CPU *cpu = X86_CPU(s);
5645 X86CPUClass *xcc = X86_CPU_GET_CLASS(cpu);
5646 CPUX86State *env = &cpu->env;
5647 target_ulong cr4;
5648 uint64_t xcr0;
5649 int i;
5651 xcc->parent_reset(dev);
5653 memset(env, 0, offsetof(CPUX86State, end_reset_fields));
5655 env->old_exception = -1;
5657 /* init to reset state */
5658 env->int_ctl = 0;
5659 env->hflags2 |= HF2_GIF_MASK;
5660 env->hflags2 |= HF2_VGIF_MASK;
5661 env->hflags &= ~HF_GUEST_MASK;
5663 cpu_x86_update_cr0(env, 0x60000010);
5664 env->a20_mask = ~0x0;
5665 env->smbase = 0x30000;
5666 env->msr_smi_count = 0;
5668 env->idt.limit = 0xffff;
5669 env->gdt.limit = 0xffff;
5670 env->ldt.limit = 0xffff;
5671 env->ldt.flags = DESC_P_MASK | (2 << DESC_TYPE_SHIFT);
5672 env->tr.limit = 0xffff;
5673 env->tr.flags = DESC_P_MASK | (11 << DESC_TYPE_SHIFT);
5675 cpu_x86_load_seg_cache(env, R_CS, 0xf000, 0xffff0000, 0xffff,
5676 DESC_P_MASK | DESC_S_MASK | DESC_CS_MASK |
5677 DESC_R_MASK | DESC_A_MASK);
5678 cpu_x86_load_seg_cache(env, R_DS, 0, 0, 0xffff,
5679 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
5680 DESC_A_MASK);
5681 cpu_x86_load_seg_cache(env, R_ES, 0, 0, 0xffff,
5682 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
5683 DESC_A_MASK);
5684 cpu_x86_load_seg_cache(env, R_SS, 0, 0, 0xffff,
5685 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
5686 DESC_A_MASK);
5687 cpu_x86_load_seg_cache(env, R_FS, 0, 0, 0xffff,
5688 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
5689 DESC_A_MASK);
5690 cpu_x86_load_seg_cache(env, R_GS, 0, 0, 0xffff,
5691 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
5692 DESC_A_MASK);
5694 env->eip = 0xfff0;
5695 env->regs[R_EDX] = env->cpuid_version;
5697 env->eflags = 0x2;
5699 /* FPU init */
5700 for (i = 0; i < 8; i++) {
5701 env->fptags[i] = 1;
5703 cpu_set_fpuc(env, 0x37f);
5705 env->mxcsr = 0x1f80;
5706 /* All units are in INIT state. */
5707 env->xstate_bv = 0;
5709 env->pat = 0x0007040600070406ULL;
5710 env->msr_ia32_misc_enable = MSR_IA32_MISC_ENABLE_DEFAULT;
5711 if (env->features[FEAT_1_ECX] & CPUID_EXT_MONITOR) {
5712 env->msr_ia32_misc_enable |= MSR_IA32_MISC_ENABLE_MWAIT;
5715 memset(env->dr, 0, sizeof(env->dr));
5716 env->dr[6] = DR6_FIXED_1;
5717 env->dr[7] = DR7_FIXED_1;
5718 cpu_breakpoint_remove_all(s, BP_CPU);
5719 cpu_watchpoint_remove_all(s, BP_CPU);
5721 cr4 = 0;
5722 xcr0 = XSTATE_FP_MASK;
5724 #ifdef CONFIG_USER_ONLY
5725 /* Enable all the features for user-mode. */
5726 if (env->features[FEAT_1_EDX] & CPUID_SSE) {
5727 xcr0 |= XSTATE_SSE_MASK;
5729 for (i = 2; i < ARRAY_SIZE(x86_ext_save_areas); i++) {
5730 const ExtSaveArea *esa = &x86_ext_save_areas[i];
5731 if (env->features[esa->feature] & esa->bits) {
5732 xcr0 |= 1ull << i;
5736 if (env->features[FEAT_1_ECX] & CPUID_EXT_XSAVE) {
5737 cr4 |= CR4_OSFXSR_MASK | CR4_OSXSAVE_MASK;
5739 if (env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_FSGSBASE) {
5740 cr4 |= CR4_FSGSBASE_MASK;
5742 #endif
5744 env->xcr0 = xcr0;
5745 cpu_x86_update_cr4(env, cr4);
5748 * SDM 11.11.5 requires:
5749 * - IA32_MTRR_DEF_TYPE MSR.E = 0
5750 * - IA32_MTRR_PHYSMASKn.V = 0
5751 * All other bits are undefined. For simplification, zero it all.
5753 env->mtrr_deftype = 0;
5754 memset(env->mtrr_var, 0, sizeof(env->mtrr_var));
5755 memset(env->mtrr_fixed, 0, sizeof(env->mtrr_fixed));
5757 env->interrupt_injected = -1;
5758 env->exception_nr = -1;
5759 env->exception_pending = 0;
5760 env->exception_injected = 0;
5761 env->exception_has_payload = false;
5762 env->exception_payload = 0;
5763 env->nmi_injected = false;
5764 #if !defined(CONFIG_USER_ONLY)
5765 /* We hard-wire the BSP to the first CPU. */
5766 apic_designate_bsp(cpu->apic_state, s->cpu_index == 0);
5768 s->halted = !cpu_is_bsp(cpu);
5770 if (kvm_enabled()) {
5771 kvm_arch_reset_vcpu(cpu);
5773 #endif
5776 static void mce_init(X86CPU *cpu)
5778 CPUX86State *cenv = &cpu->env;
5779 unsigned int bank;
5781 if (((cenv->cpuid_version >> 8) & 0xf) >= 6
5782 && (cenv->features[FEAT_1_EDX] & (CPUID_MCE | CPUID_MCA)) ==
5783 (CPUID_MCE | CPUID_MCA)) {
5784 cenv->mcg_cap = MCE_CAP_DEF | MCE_BANKS_DEF |
5785 (cpu->enable_lmce ? MCG_LMCE_P : 0);
5786 cenv->mcg_ctl = ~(uint64_t)0;
5787 for (bank = 0; bank < MCE_BANKS_DEF; bank++) {
5788 cenv->mce_banks[bank * 4] = ~(uint64_t)0;
5793 static void x86_cpu_adjust_level(X86CPU *cpu, uint32_t *min, uint32_t value)
5795 if (*min < value) {
5796 *min = value;
5800 /* Increase cpuid_min_{level,xlevel,xlevel2} automatically, if appropriate */
5801 static void x86_cpu_adjust_feat_level(X86CPU *cpu, FeatureWord w)
5803 CPUX86State *env = &cpu->env;
5804 FeatureWordInfo *fi = &feature_word_info[w];
5805 uint32_t eax = fi->cpuid.eax;
5806 uint32_t region = eax & 0xF0000000;
5808 assert(feature_word_info[w].type == CPUID_FEATURE_WORD);
5809 if (!env->features[w]) {
5810 return;
5813 switch (region) {
5814 case 0x00000000:
5815 x86_cpu_adjust_level(cpu, &env->cpuid_min_level, eax);
5816 break;
5817 case 0x80000000:
5818 x86_cpu_adjust_level(cpu, &env->cpuid_min_xlevel, eax);
5819 break;
5820 case 0xC0000000:
5821 x86_cpu_adjust_level(cpu, &env->cpuid_min_xlevel2, eax);
5822 break;
5825 if (eax == 7) {
5826 x86_cpu_adjust_level(cpu, &env->cpuid_min_level_func7,
5827 fi->cpuid.ecx);
5831 /* Calculate XSAVE components based on the configured CPU feature flags */
5832 static void x86_cpu_enable_xsave_components(X86CPU *cpu)
5834 CPUX86State *env = &cpu->env;
5835 int i;
5836 uint64_t mask;
5838 if (!(env->features[FEAT_1_ECX] & CPUID_EXT_XSAVE)) {
5839 env->features[FEAT_XSAVE_COMP_LO] = 0;
5840 env->features[FEAT_XSAVE_COMP_HI] = 0;
5841 return;
5844 mask = 0;
5845 for (i = 0; i < ARRAY_SIZE(x86_ext_save_areas); i++) {
5846 const ExtSaveArea *esa = &x86_ext_save_areas[i];
5847 if (env->features[esa->feature] & esa->bits) {
5848 mask |= (1ULL << i);
5852 env->features[FEAT_XSAVE_COMP_LO] = mask;
5853 env->features[FEAT_XSAVE_COMP_HI] = mask >> 32;
5856 /***** Steps involved on loading and filtering CPUID data
5858 * When initializing and realizing a CPU object, the steps
5859 * involved in setting up CPUID data are:
5861 * 1) Loading CPU model definition (X86CPUDefinition). This is
5862 * implemented by x86_cpu_load_model() and should be completely
5863 * transparent, as it is done automatically by instance_init.
5864 * No code should need to look at X86CPUDefinition structs
5865 * outside instance_init.
5867 * 2) CPU expansion. This is done by realize before CPUID
5868 * filtering, and will make sure host/accelerator data is
5869 * loaded for CPU models that depend on host capabilities
5870 * (e.g. "host"). Done by x86_cpu_expand_features().
5872 * 3) CPUID filtering. This initializes extra data related to
5873 * CPUID, and checks if the host supports all capabilities
5874 * required by the CPU. Runnability of a CPU model is
5875 * determined at this step. Done by x86_cpu_filter_features().
5877 * Some operations don't require all steps to be performed.
5878 * More precisely:
5880 * - CPU instance creation (instance_init) will run only CPU
5881 * model loading. CPU expansion can't run at instance_init-time
5882 * because host/accelerator data may be not available yet.
5883 * - CPU realization will perform both CPU model expansion and CPUID
5884 * filtering, and return an error in case one of them fails.
5885 * - query-cpu-definitions needs to run all 3 steps. It needs
5886 * to run CPUID filtering, as the 'unavailable-features'
5887 * field is set based on the filtering results.
5888 * - The query-cpu-model-expansion QMP command only needs to run
5889 * CPU model loading and CPU expansion. It should not filter
5890 * any CPUID data based on host capabilities.
5893 /* Expand CPU configuration data, based on configured features
5894 * and host/accelerator capabilities when appropriate.
5896 void x86_cpu_expand_features(X86CPU *cpu, Error **errp)
5898 CPUX86State *env = &cpu->env;
5899 FeatureWord w;
5900 int i;
5901 GList *l;
5903 for (l = plus_features; l; l = l->next) {
5904 const char *prop = l->data;
5905 if (!object_property_set_bool(OBJECT(cpu), prop, true, errp)) {
5906 return;
5910 for (l = minus_features; l; l = l->next) {
5911 const char *prop = l->data;
5912 if (!object_property_set_bool(OBJECT(cpu), prop, false, errp)) {
5913 return;
5917 /*TODO: Now cpu->max_features doesn't overwrite features
5918 * set using QOM properties, and we can convert
5919 * plus_features & minus_features to global properties
5920 * inside x86_cpu_parse_featurestr() too.
5922 if (cpu->max_features) {
5923 for (w = 0; w < FEATURE_WORDS; w++) {
5924 /* Override only features that weren't set explicitly
5925 * by the user.
5927 env->features[w] |=
5928 x86_cpu_get_supported_feature_word(w, cpu->migratable) &
5929 ~env->user_features[w] &
5930 ~feature_word_info[w].no_autoenable_flags;
5934 for (i = 0; i < ARRAY_SIZE(feature_dependencies); i++) {
5935 FeatureDep *d = &feature_dependencies[i];
5936 if (!(env->features[d->from.index] & d->from.mask)) {
5937 uint64_t unavailable_features = env->features[d->to.index] & d->to.mask;
5939 /* Not an error unless the dependent feature was added explicitly. */
5940 mark_unavailable_features(cpu, d->to.index,
5941 unavailable_features & env->user_features[d->to.index],
5942 "This feature depends on other features that were not requested");
5944 env->features[d->to.index] &= ~unavailable_features;
5948 if (!kvm_enabled() || !cpu->expose_kvm) {
5949 env->features[FEAT_KVM] = 0;
5952 x86_cpu_enable_xsave_components(cpu);
5954 /* CPUID[EAX=7,ECX=0].EBX always increased level automatically: */
5955 x86_cpu_adjust_feat_level(cpu, FEAT_7_0_EBX);
5956 if (cpu->full_cpuid_auto_level) {
5957 x86_cpu_adjust_feat_level(cpu, FEAT_1_EDX);
5958 x86_cpu_adjust_feat_level(cpu, FEAT_1_ECX);
5959 x86_cpu_adjust_feat_level(cpu, FEAT_6_EAX);
5960 x86_cpu_adjust_feat_level(cpu, FEAT_7_0_ECX);
5961 x86_cpu_adjust_feat_level(cpu, FEAT_7_1_EAX);
5962 x86_cpu_adjust_feat_level(cpu, FEAT_8000_0001_EDX);
5963 x86_cpu_adjust_feat_level(cpu, FEAT_8000_0001_ECX);
5964 x86_cpu_adjust_feat_level(cpu, FEAT_8000_0007_EDX);
5965 x86_cpu_adjust_feat_level(cpu, FEAT_8000_0008_EBX);
5966 x86_cpu_adjust_feat_level(cpu, FEAT_C000_0001_EDX);
5967 x86_cpu_adjust_feat_level(cpu, FEAT_SVM);
5968 x86_cpu_adjust_feat_level(cpu, FEAT_XSAVE);
5970 /* Intel Processor Trace requires CPUID[0x14] */
5971 if ((env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_INTEL_PT)) {
5972 if (cpu->intel_pt_auto_level) {
5973 x86_cpu_adjust_level(cpu, &cpu->env.cpuid_min_level, 0x14);
5974 } else if (cpu->env.cpuid_min_level < 0x14) {
5975 mark_unavailable_features(cpu, FEAT_7_0_EBX,
5976 CPUID_7_0_EBX_INTEL_PT,
5977 "Intel PT need CPUID leaf 0x14, please set by \"-cpu ...,intel-pt=on,min-level=0x14\"");
5982 * Intel CPU topology with multi-dies support requires CPUID[0x1F].
5983 * For AMD Rome/Milan, cpuid level is 0x10, and guest OS should detect
5984 * extended toplogy by leaf 0xB. Only adjust it for Intel CPU, unless
5985 * cpu->vendor_cpuid_only has been unset for compatibility with older
5986 * machine types.
5988 if ((env->nr_dies > 1) &&
5989 (IS_INTEL_CPU(env) || !cpu->vendor_cpuid_only)) {
5990 x86_cpu_adjust_level(cpu, &env->cpuid_min_level, 0x1F);
5993 /* SVM requires CPUID[0x8000000A] */
5994 if (env->features[FEAT_8000_0001_ECX] & CPUID_EXT3_SVM) {
5995 x86_cpu_adjust_level(cpu, &env->cpuid_min_xlevel, 0x8000000A);
5998 /* SEV requires CPUID[0x8000001F] */
5999 if (sev_enabled()) {
6000 x86_cpu_adjust_level(cpu, &env->cpuid_min_xlevel, 0x8000001F);
6004 /* Set cpuid_*level* based on cpuid_min_*level, if not explicitly set */
6005 if (env->cpuid_level_func7 == UINT32_MAX) {
6006 env->cpuid_level_func7 = env->cpuid_min_level_func7;
6008 if (env->cpuid_level == UINT32_MAX) {
6009 env->cpuid_level = env->cpuid_min_level;
6011 if (env->cpuid_xlevel == UINT32_MAX) {
6012 env->cpuid_xlevel = env->cpuid_min_xlevel;
6014 if (env->cpuid_xlevel2 == UINT32_MAX) {
6015 env->cpuid_xlevel2 = env->cpuid_min_xlevel2;
6018 if (kvm_enabled()) {
6019 kvm_hyperv_expand_features(cpu, errp);
6024 * Finishes initialization of CPUID data, filters CPU feature
6025 * words based on host availability of each feature.
6027 * Returns: 0 if all flags are supported by the host, non-zero otherwise.
6029 static void x86_cpu_filter_features(X86CPU *cpu, bool verbose)
6031 CPUX86State *env = &cpu->env;
6032 FeatureWord w;
6033 const char *prefix = NULL;
6035 if (verbose) {
6036 prefix = accel_uses_host_cpuid()
6037 ? "host doesn't support requested feature"
6038 : "TCG doesn't support requested feature";
6041 for (w = 0; w < FEATURE_WORDS; w++) {
6042 uint64_t host_feat =
6043 x86_cpu_get_supported_feature_word(w, false);
6044 uint64_t requested_features = env->features[w];
6045 uint64_t unavailable_features = requested_features & ~host_feat;
6046 mark_unavailable_features(cpu, w, unavailable_features, prefix);
6049 if ((env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_INTEL_PT) &&
6050 kvm_enabled()) {
6051 KVMState *s = CPU(cpu)->kvm_state;
6052 uint32_t eax_0 = kvm_arch_get_supported_cpuid(s, 0x14, 0, R_EAX);
6053 uint32_t ebx_0 = kvm_arch_get_supported_cpuid(s, 0x14, 0, R_EBX);
6054 uint32_t ecx_0 = kvm_arch_get_supported_cpuid(s, 0x14, 0, R_ECX);
6055 uint32_t eax_1 = kvm_arch_get_supported_cpuid(s, 0x14, 1, R_EAX);
6056 uint32_t ebx_1 = kvm_arch_get_supported_cpuid(s, 0x14, 1, R_EBX);
6058 if (!eax_0 ||
6059 ((ebx_0 & INTEL_PT_MINIMAL_EBX) != INTEL_PT_MINIMAL_EBX) ||
6060 ((ecx_0 & INTEL_PT_MINIMAL_ECX) != INTEL_PT_MINIMAL_ECX) ||
6061 ((eax_1 & INTEL_PT_MTC_BITMAP) != INTEL_PT_MTC_BITMAP) ||
6062 ((eax_1 & INTEL_PT_ADDR_RANGES_NUM_MASK) <
6063 INTEL_PT_ADDR_RANGES_NUM) ||
6064 ((ebx_1 & (INTEL_PT_PSB_BITMAP | INTEL_PT_CYCLE_BITMAP)) !=
6065 (INTEL_PT_PSB_BITMAP | INTEL_PT_CYCLE_BITMAP)) ||
6066 ((ecx_0 & CPUID_14_0_ECX_LIP) !=
6067 (env->features[FEAT_14_0_ECX] & CPUID_14_0_ECX_LIP))) {
6069 * Processor Trace capabilities aren't configurable, so if the
6070 * host can't emulate the capabilities we report on
6071 * cpu_x86_cpuid(), intel-pt can't be enabled on the current host.
6073 mark_unavailable_features(cpu, FEAT_7_0_EBX, CPUID_7_0_EBX_INTEL_PT, prefix);
6078 static void x86_cpu_hyperv_realize(X86CPU *cpu)
6080 size_t len;
6082 /* Hyper-V vendor id */
6083 if (!cpu->hyperv_vendor) {
6084 object_property_set_str(OBJECT(cpu), "hv-vendor-id", "Microsoft Hv",
6085 &error_abort);
6087 len = strlen(cpu->hyperv_vendor);
6088 if (len > 12) {
6089 warn_report("hv-vendor-id truncated to 12 characters");
6090 len = 12;
6092 memset(cpu->hyperv_vendor_id, 0, 12);
6093 memcpy(cpu->hyperv_vendor_id, cpu->hyperv_vendor, len);
6095 /* 'Hv#1' interface identification*/
6096 cpu->hyperv_interface_id[0] = 0x31237648;
6097 cpu->hyperv_interface_id[1] = 0;
6098 cpu->hyperv_interface_id[2] = 0;
6099 cpu->hyperv_interface_id[3] = 0;
6101 /* Hypervisor system identity */
6102 cpu->hyperv_version_id[0] = 0x00001bbc;
6103 cpu->hyperv_version_id[1] = 0x00060001;
6105 /* Hypervisor implementation limits */
6106 cpu->hyperv_limits[0] = 64;
6107 cpu->hyperv_limits[1] = 0;
6108 cpu->hyperv_limits[2] = 0;
6111 static void x86_cpu_realizefn(DeviceState *dev, Error **errp)
6113 CPUState *cs = CPU(dev);
6114 X86CPU *cpu = X86_CPU(dev);
6115 X86CPUClass *xcc = X86_CPU_GET_CLASS(dev);
6116 CPUX86State *env = &cpu->env;
6117 Error *local_err = NULL;
6118 static bool ht_warned;
6120 if (cpu->apic_id == UNASSIGNED_APIC_ID) {
6121 error_setg(errp, "apic-id property was not initialized properly");
6122 return;
6126 * Process Hyper-V enlightenments.
6127 * Note: this currently has to happen before the expansion of CPU features.
6129 x86_cpu_hyperv_realize(cpu);
6131 x86_cpu_expand_features(cpu, &local_err);
6132 if (local_err) {
6133 goto out;
6136 x86_cpu_filter_features(cpu, cpu->check_cpuid || cpu->enforce_cpuid);
6138 if (cpu->enforce_cpuid && x86_cpu_have_filtered_features(cpu)) {
6139 error_setg(&local_err,
6140 accel_uses_host_cpuid() ?
6141 "Host doesn't support requested features" :
6142 "TCG doesn't support requested features");
6143 goto out;
6146 /* On AMD CPUs, some CPUID[8000_0001].EDX bits must match the bits on
6147 * CPUID[1].EDX.
6149 if (IS_AMD_CPU(env)) {
6150 env->features[FEAT_8000_0001_EDX] &= ~CPUID_EXT2_AMD_ALIASES;
6151 env->features[FEAT_8000_0001_EDX] |= (env->features[FEAT_1_EDX]
6152 & CPUID_EXT2_AMD_ALIASES);
6156 * note: the call to the framework needs to happen after feature expansion,
6157 * but before the checks/modifications to ucode_rev, mwait, phys_bits.
6158 * These may be set by the accel-specific code,
6159 * and the results are subsequently checked / assumed in this function.
6161 cpu_exec_realizefn(cs, &local_err);
6162 if (local_err != NULL) {
6163 error_propagate(errp, local_err);
6164 return;
6167 if (xcc->host_cpuid_required && !accel_uses_host_cpuid()) {
6168 g_autofree char *name = x86_cpu_class_get_model_name(xcc);
6169 error_setg(&local_err, "CPU model '%s' requires KVM or HVF", name);
6170 goto out;
6173 if (cpu->ucode_rev == 0) {
6175 * The default is the same as KVM's. Note that this check
6176 * needs to happen after the evenual setting of ucode_rev in
6177 * accel-specific code in cpu_exec_realizefn.
6179 if (IS_AMD_CPU(env)) {
6180 cpu->ucode_rev = 0x01000065;
6181 } else {
6182 cpu->ucode_rev = 0x100000000ULL;
6187 * mwait extended info: needed for Core compatibility
6188 * We always wake on interrupt even if host does not have the capability.
6190 * requires the accel-specific code in cpu_exec_realizefn to
6191 * have already acquired the CPUID data into cpu->mwait.
6193 cpu->mwait.ecx |= CPUID_MWAIT_EMX | CPUID_MWAIT_IBE;
6195 /* For 64bit systems think about the number of physical bits to present.
6196 * ideally this should be the same as the host; anything other than matching
6197 * the host can cause incorrect guest behaviour.
6198 * QEMU used to pick the magic value of 40 bits that corresponds to
6199 * consumer AMD devices but nothing else.
6201 * Note that this code assumes features expansion has already been done
6202 * (as it checks for CPUID_EXT2_LM), and also assumes that potential
6203 * phys_bits adjustments to match the host have been already done in
6204 * accel-specific code in cpu_exec_realizefn.
6206 if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_LM) {
6207 if (cpu->phys_bits &&
6208 (cpu->phys_bits > TARGET_PHYS_ADDR_SPACE_BITS ||
6209 cpu->phys_bits < 32)) {
6210 error_setg(errp, "phys-bits should be between 32 and %u "
6211 " (but is %u)",
6212 TARGET_PHYS_ADDR_SPACE_BITS, cpu->phys_bits);
6213 return;
6216 * 0 means it was not explicitly set by the user (or by machine
6217 * compat_props or by the host code in host-cpu.c).
6218 * In this case, the default is the value used by TCG (40).
6220 if (cpu->phys_bits == 0) {
6221 cpu->phys_bits = TCG_PHYS_ADDR_BITS;
6223 } else {
6224 /* For 32 bit systems don't use the user set value, but keep
6225 * phys_bits consistent with what we tell the guest.
6227 if (cpu->phys_bits != 0) {
6228 error_setg(errp, "phys-bits is not user-configurable in 32 bit");
6229 return;
6232 if (env->features[FEAT_1_EDX] & CPUID_PSE36) {
6233 cpu->phys_bits = 36;
6234 } else {
6235 cpu->phys_bits = 32;
6239 /* Cache information initialization */
6240 if (!cpu->legacy_cache) {
6241 if (!xcc->model || !xcc->model->cpudef->cache_info) {
6242 g_autofree char *name = x86_cpu_class_get_model_name(xcc);
6243 error_setg(errp,
6244 "CPU model '%s' doesn't support legacy-cache=off", name);
6245 return;
6247 env->cache_info_cpuid2 = env->cache_info_cpuid4 = env->cache_info_amd =
6248 *xcc->model->cpudef->cache_info;
6249 } else {
6250 /* Build legacy cache information */
6251 env->cache_info_cpuid2.l1d_cache = &legacy_l1d_cache;
6252 env->cache_info_cpuid2.l1i_cache = &legacy_l1i_cache;
6253 env->cache_info_cpuid2.l2_cache = &legacy_l2_cache_cpuid2;
6254 env->cache_info_cpuid2.l3_cache = &legacy_l3_cache;
6256 env->cache_info_cpuid4.l1d_cache = &legacy_l1d_cache;
6257 env->cache_info_cpuid4.l1i_cache = &legacy_l1i_cache;
6258 env->cache_info_cpuid4.l2_cache = &legacy_l2_cache;
6259 env->cache_info_cpuid4.l3_cache = &legacy_l3_cache;
6261 env->cache_info_amd.l1d_cache = &legacy_l1d_cache_amd;
6262 env->cache_info_amd.l1i_cache = &legacy_l1i_cache_amd;
6263 env->cache_info_amd.l2_cache = &legacy_l2_cache_amd;
6264 env->cache_info_amd.l3_cache = &legacy_l3_cache;
6267 #ifndef CONFIG_USER_ONLY
6268 MachineState *ms = MACHINE(qdev_get_machine());
6269 qemu_register_reset(x86_cpu_machine_reset_cb, cpu);
6271 if (cpu->env.features[FEAT_1_EDX] & CPUID_APIC || ms->smp.cpus > 1) {
6272 x86_cpu_apic_create(cpu, &local_err);
6273 if (local_err != NULL) {
6274 goto out;
6277 #endif
6279 mce_init(cpu);
6281 qemu_init_vcpu(cs);
6284 * Most Intel and certain AMD CPUs support hyperthreading. Even though QEMU
6285 * fixes this issue by adjusting CPUID_0000_0001_EBX and CPUID_8000_0008_ECX
6286 * based on inputs (sockets,cores,threads), it is still better to give
6287 * users a warning.
6289 * NOTE: the following code has to follow qemu_init_vcpu(). Otherwise
6290 * cs->nr_threads hasn't be populated yet and the checking is incorrect.
6292 if (IS_AMD_CPU(env) &&
6293 !(env->features[FEAT_8000_0001_ECX] & CPUID_EXT3_TOPOEXT) &&
6294 cs->nr_threads > 1 && !ht_warned) {
6295 warn_report("This family of AMD CPU doesn't support "
6296 "hyperthreading(%d)",
6297 cs->nr_threads);
6298 error_printf("Please configure -smp options properly"
6299 " or try enabling topoext feature.\n");
6300 ht_warned = true;
6303 #ifndef CONFIG_USER_ONLY
6304 x86_cpu_apic_realize(cpu, &local_err);
6305 if (local_err != NULL) {
6306 goto out;
6308 #endif /* !CONFIG_USER_ONLY */
6309 cpu_reset(cs);
6311 xcc->parent_realize(dev, &local_err);
6313 out:
6314 if (local_err != NULL) {
6315 error_propagate(errp, local_err);
6316 return;
6320 static void x86_cpu_unrealizefn(DeviceState *dev)
6322 X86CPU *cpu = X86_CPU(dev);
6323 X86CPUClass *xcc = X86_CPU_GET_CLASS(dev);
6325 #ifndef CONFIG_USER_ONLY
6326 cpu_remove_sync(CPU(dev));
6327 qemu_unregister_reset(x86_cpu_machine_reset_cb, dev);
6328 #endif
6330 if (cpu->apic_state) {
6331 object_unparent(OBJECT(cpu->apic_state));
6332 cpu->apic_state = NULL;
6335 xcc->parent_unrealize(dev);
6338 typedef struct BitProperty {
6339 FeatureWord w;
6340 uint64_t mask;
6341 } BitProperty;
6343 static void x86_cpu_get_bit_prop(Object *obj, Visitor *v, const char *name,
6344 void *opaque, Error **errp)
6346 X86CPU *cpu = X86_CPU(obj);
6347 BitProperty *fp = opaque;
6348 uint64_t f = cpu->env.features[fp->w];
6349 bool value = (f & fp->mask) == fp->mask;
6350 visit_type_bool(v, name, &value, errp);
6353 static void x86_cpu_set_bit_prop(Object *obj, Visitor *v, const char *name,
6354 void *opaque, Error **errp)
6356 DeviceState *dev = DEVICE(obj);
6357 X86CPU *cpu = X86_CPU(obj);
6358 BitProperty *fp = opaque;
6359 bool value;
6361 if (dev->realized) {
6362 qdev_prop_set_after_realize(dev, name, errp);
6363 return;
6366 if (!visit_type_bool(v, name, &value, errp)) {
6367 return;
6370 if (value) {
6371 cpu->env.features[fp->w] |= fp->mask;
6372 } else {
6373 cpu->env.features[fp->w] &= ~fp->mask;
6375 cpu->env.user_features[fp->w] |= fp->mask;
6378 /* Register a boolean property to get/set a single bit in a uint32_t field.
6380 * The same property name can be registered multiple times to make it affect
6381 * multiple bits in the same FeatureWord. In that case, the getter will return
6382 * true only if all bits are set.
6384 static void x86_cpu_register_bit_prop(X86CPUClass *xcc,
6385 const char *prop_name,
6386 FeatureWord w,
6387 int bitnr)
6389 ObjectClass *oc = OBJECT_CLASS(xcc);
6390 BitProperty *fp;
6391 ObjectProperty *op;
6392 uint64_t mask = (1ULL << bitnr);
6394 op = object_class_property_find(oc, prop_name);
6395 if (op) {
6396 fp = op->opaque;
6397 assert(fp->w == w);
6398 fp->mask |= mask;
6399 } else {
6400 fp = g_new0(BitProperty, 1);
6401 fp->w = w;
6402 fp->mask = mask;
6403 object_class_property_add(oc, prop_name, "bool",
6404 x86_cpu_get_bit_prop,
6405 x86_cpu_set_bit_prop,
6406 NULL, fp);
6410 static void x86_cpu_register_feature_bit_props(X86CPUClass *xcc,
6411 FeatureWord w,
6412 int bitnr)
6414 FeatureWordInfo *fi = &feature_word_info[w];
6415 const char *name = fi->feat_names[bitnr];
6417 if (!name) {
6418 return;
6421 /* Property names should use "-" instead of "_".
6422 * Old names containing underscores are registered as aliases
6423 * using object_property_add_alias()
6425 assert(!strchr(name, '_'));
6426 /* aliases don't use "|" delimiters anymore, they are registered
6427 * manually using object_property_add_alias() */
6428 assert(!strchr(name, '|'));
6429 x86_cpu_register_bit_prop(xcc, name, w, bitnr);
6432 static void x86_cpu_post_initfn(Object *obj)
6434 accel_cpu_instance_init(CPU(obj));
6437 static void x86_cpu_initfn(Object *obj)
6439 X86CPU *cpu = X86_CPU(obj);
6440 X86CPUClass *xcc = X86_CPU_GET_CLASS(obj);
6441 CPUX86State *env = &cpu->env;
6443 env->nr_dies = 1;
6444 cpu_set_cpustate_pointers(cpu);
6446 object_property_add(obj, "feature-words", "X86CPUFeatureWordInfo",
6447 x86_cpu_get_feature_words,
6448 NULL, NULL, (void *)env->features);
6449 object_property_add(obj, "filtered-features", "X86CPUFeatureWordInfo",
6450 x86_cpu_get_feature_words,
6451 NULL, NULL, (void *)cpu->filtered_features);
6453 object_property_add_alias(obj, "sse3", obj, "pni");
6454 object_property_add_alias(obj, "pclmuldq", obj, "pclmulqdq");
6455 object_property_add_alias(obj, "sse4-1", obj, "sse4.1");
6456 object_property_add_alias(obj, "sse4-2", obj, "sse4.2");
6457 object_property_add_alias(obj, "xd", obj, "nx");
6458 object_property_add_alias(obj, "ffxsr", obj, "fxsr-opt");
6459 object_property_add_alias(obj, "i64", obj, "lm");
6461 object_property_add_alias(obj, "ds_cpl", obj, "ds-cpl");
6462 object_property_add_alias(obj, "tsc_adjust", obj, "tsc-adjust");
6463 object_property_add_alias(obj, "fxsr_opt", obj, "fxsr-opt");
6464 object_property_add_alias(obj, "lahf_lm", obj, "lahf-lm");
6465 object_property_add_alias(obj, "cmp_legacy", obj, "cmp-legacy");
6466 object_property_add_alias(obj, "nodeid_msr", obj, "nodeid-msr");
6467 object_property_add_alias(obj, "perfctr_core", obj, "perfctr-core");
6468 object_property_add_alias(obj, "perfctr_nb", obj, "perfctr-nb");
6469 object_property_add_alias(obj, "kvm_nopiodelay", obj, "kvm-nopiodelay");
6470 object_property_add_alias(obj, "kvm_mmu", obj, "kvm-mmu");
6471 object_property_add_alias(obj, "kvm_asyncpf", obj, "kvm-asyncpf");
6472 object_property_add_alias(obj, "kvm_asyncpf_int", obj, "kvm-asyncpf-int");
6473 object_property_add_alias(obj, "kvm_steal_time", obj, "kvm-steal-time");
6474 object_property_add_alias(obj, "kvm_pv_eoi", obj, "kvm-pv-eoi");
6475 object_property_add_alias(obj, "kvm_pv_unhalt", obj, "kvm-pv-unhalt");
6476 object_property_add_alias(obj, "kvm_poll_control", obj, "kvm-poll-control");
6477 object_property_add_alias(obj, "svm_lock", obj, "svm-lock");
6478 object_property_add_alias(obj, "nrip_save", obj, "nrip-save");
6479 object_property_add_alias(obj, "tsc_scale", obj, "tsc-scale");
6480 object_property_add_alias(obj, "vmcb_clean", obj, "vmcb-clean");
6481 object_property_add_alias(obj, "pause_filter", obj, "pause-filter");
6482 object_property_add_alias(obj, "sse4_1", obj, "sse4.1");
6483 object_property_add_alias(obj, "sse4_2", obj, "sse4.2");
6485 if (xcc->model) {
6486 x86_cpu_load_model(cpu, xcc->model);
6490 static int64_t x86_cpu_get_arch_id(CPUState *cs)
6492 X86CPU *cpu = X86_CPU(cs);
6494 return cpu->apic_id;
6497 #if !defined(CONFIG_USER_ONLY)
6498 static bool x86_cpu_get_paging_enabled(const CPUState *cs)
6500 X86CPU *cpu = X86_CPU(cs);
6502 return cpu->env.cr[0] & CR0_PG_MASK;
6504 #endif /* !CONFIG_USER_ONLY */
6506 static void x86_cpu_set_pc(CPUState *cs, vaddr value)
6508 X86CPU *cpu = X86_CPU(cs);
6510 cpu->env.eip = value;
6513 int x86_cpu_pending_interrupt(CPUState *cs, int interrupt_request)
6515 X86CPU *cpu = X86_CPU(cs);
6516 CPUX86State *env = &cpu->env;
6518 #if !defined(CONFIG_USER_ONLY)
6519 if (interrupt_request & CPU_INTERRUPT_POLL) {
6520 return CPU_INTERRUPT_POLL;
6522 #endif
6523 if (interrupt_request & CPU_INTERRUPT_SIPI) {
6524 return CPU_INTERRUPT_SIPI;
6527 if (env->hflags2 & HF2_GIF_MASK) {
6528 if ((interrupt_request & CPU_INTERRUPT_SMI) &&
6529 !(env->hflags & HF_SMM_MASK)) {
6530 return CPU_INTERRUPT_SMI;
6531 } else if ((interrupt_request & CPU_INTERRUPT_NMI) &&
6532 !(env->hflags2 & HF2_NMI_MASK)) {
6533 return CPU_INTERRUPT_NMI;
6534 } else if (interrupt_request & CPU_INTERRUPT_MCE) {
6535 return CPU_INTERRUPT_MCE;
6536 } else if ((interrupt_request & CPU_INTERRUPT_HARD) &&
6537 (((env->hflags2 & HF2_VINTR_MASK) &&
6538 (env->hflags2 & HF2_HIF_MASK)) ||
6539 (!(env->hflags2 & HF2_VINTR_MASK) &&
6540 (env->eflags & IF_MASK &&
6541 !(env->hflags & HF_INHIBIT_IRQ_MASK))))) {
6542 return CPU_INTERRUPT_HARD;
6543 #if !defined(CONFIG_USER_ONLY)
6544 } else if (env->hflags2 & HF2_VGIF_MASK) {
6545 if((interrupt_request & CPU_INTERRUPT_VIRQ) &&
6546 (env->eflags & IF_MASK) &&
6547 !(env->hflags & HF_INHIBIT_IRQ_MASK)) {
6548 return CPU_INTERRUPT_VIRQ;
6550 #endif
6554 return 0;
6557 static bool x86_cpu_has_work(CPUState *cs)
6559 return x86_cpu_pending_interrupt(cs, cs->interrupt_request) != 0;
6562 static void x86_disas_set_info(CPUState *cs, disassemble_info *info)
6564 X86CPU *cpu = X86_CPU(cs);
6565 CPUX86State *env = &cpu->env;
6567 info->mach = (env->hflags & HF_CS64_MASK ? bfd_mach_x86_64
6568 : env->hflags & HF_CS32_MASK ? bfd_mach_i386_i386
6569 : bfd_mach_i386_i8086);
6570 info->print_insn = print_insn_i386;
6572 info->cap_arch = CS_ARCH_X86;
6573 info->cap_mode = (env->hflags & HF_CS64_MASK ? CS_MODE_64
6574 : env->hflags & HF_CS32_MASK ? CS_MODE_32
6575 : CS_MODE_16);
6576 info->cap_insn_unit = 1;
6577 info->cap_insn_split = 8;
6580 void x86_update_hflags(CPUX86State *env)
6582 uint32_t hflags;
6583 #define HFLAG_COPY_MASK \
6584 ~( HF_CPL_MASK | HF_PE_MASK | HF_MP_MASK | HF_EM_MASK | \
6585 HF_TS_MASK | HF_TF_MASK | HF_VM_MASK | HF_IOPL_MASK | \
6586 HF_OSFXSR_MASK | HF_LMA_MASK | HF_CS32_MASK | \
6587 HF_SS32_MASK | HF_CS64_MASK | HF_ADDSEG_MASK)
6589 hflags = env->hflags & HFLAG_COPY_MASK;
6590 hflags |= (env->segs[R_SS].flags >> DESC_DPL_SHIFT) & HF_CPL_MASK;
6591 hflags |= (env->cr[0] & CR0_PE_MASK) << (HF_PE_SHIFT - CR0_PE_SHIFT);
6592 hflags |= (env->cr[0] << (HF_MP_SHIFT - CR0_MP_SHIFT)) &
6593 (HF_MP_MASK | HF_EM_MASK | HF_TS_MASK);
6594 hflags |= (env->eflags & (HF_TF_MASK | HF_VM_MASK | HF_IOPL_MASK));
6596 if (env->cr[4] & CR4_OSFXSR_MASK) {
6597 hflags |= HF_OSFXSR_MASK;
6600 if (env->efer & MSR_EFER_LMA) {
6601 hflags |= HF_LMA_MASK;
6604 if ((hflags & HF_LMA_MASK) && (env->segs[R_CS].flags & DESC_L_MASK)) {
6605 hflags |= HF_CS32_MASK | HF_SS32_MASK | HF_CS64_MASK;
6606 } else {
6607 hflags |= (env->segs[R_CS].flags & DESC_B_MASK) >>
6608 (DESC_B_SHIFT - HF_CS32_SHIFT);
6609 hflags |= (env->segs[R_SS].flags & DESC_B_MASK) >>
6610 (DESC_B_SHIFT - HF_SS32_SHIFT);
6611 if (!(env->cr[0] & CR0_PE_MASK) || (env->eflags & VM_MASK) ||
6612 !(hflags & HF_CS32_MASK)) {
6613 hflags |= HF_ADDSEG_MASK;
6614 } else {
6615 hflags |= ((env->segs[R_DS].base | env->segs[R_ES].base |
6616 env->segs[R_SS].base) != 0) << HF_ADDSEG_SHIFT;
6619 env->hflags = hflags;
6622 static Property x86_cpu_properties[] = {
6623 #ifdef CONFIG_USER_ONLY
6624 /* apic_id = 0 by default for *-user, see commit 9886e834 */
6625 DEFINE_PROP_UINT32("apic-id", X86CPU, apic_id, 0),
6626 DEFINE_PROP_INT32("thread-id", X86CPU, thread_id, 0),
6627 DEFINE_PROP_INT32("core-id", X86CPU, core_id, 0),
6628 DEFINE_PROP_INT32("die-id", X86CPU, die_id, 0),
6629 DEFINE_PROP_INT32("socket-id", X86CPU, socket_id, 0),
6630 #else
6631 DEFINE_PROP_UINT32("apic-id", X86CPU, apic_id, UNASSIGNED_APIC_ID),
6632 DEFINE_PROP_INT32("thread-id", X86CPU, thread_id, -1),
6633 DEFINE_PROP_INT32("core-id", X86CPU, core_id, -1),
6634 DEFINE_PROP_INT32("die-id", X86CPU, die_id, -1),
6635 DEFINE_PROP_INT32("socket-id", X86CPU, socket_id, -1),
6636 #endif
6637 DEFINE_PROP_INT32("node-id", X86CPU, node_id, CPU_UNSET_NUMA_NODE_ID),
6638 DEFINE_PROP_BOOL("pmu", X86CPU, enable_pmu, false),
6640 DEFINE_PROP_UINT32("hv-spinlocks", X86CPU, hyperv_spinlock_attempts,
6641 HYPERV_SPINLOCK_NEVER_NOTIFY),
6642 DEFINE_PROP_BIT64("hv-relaxed", X86CPU, hyperv_features,
6643 HYPERV_FEAT_RELAXED, 0),
6644 DEFINE_PROP_BIT64("hv-vapic", X86CPU, hyperv_features,
6645 HYPERV_FEAT_VAPIC, 0),
6646 DEFINE_PROP_BIT64("hv-time", X86CPU, hyperv_features,
6647 HYPERV_FEAT_TIME, 0),
6648 DEFINE_PROP_BIT64("hv-crash", X86CPU, hyperv_features,
6649 HYPERV_FEAT_CRASH, 0),
6650 DEFINE_PROP_BIT64("hv-reset", X86CPU, hyperv_features,
6651 HYPERV_FEAT_RESET, 0),
6652 DEFINE_PROP_BIT64("hv-vpindex", X86CPU, hyperv_features,
6653 HYPERV_FEAT_VPINDEX, 0),
6654 DEFINE_PROP_BIT64("hv-runtime", X86CPU, hyperv_features,
6655 HYPERV_FEAT_RUNTIME, 0),
6656 DEFINE_PROP_BIT64("hv-synic", X86CPU, hyperv_features,
6657 HYPERV_FEAT_SYNIC, 0),
6658 DEFINE_PROP_BIT64("hv-stimer", X86CPU, hyperv_features,
6659 HYPERV_FEAT_STIMER, 0),
6660 DEFINE_PROP_BIT64("hv-frequencies", X86CPU, hyperv_features,
6661 HYPERV_FEAT_FREQUENCIES, 0),
6662 DEFINE_PROP_BIT64("hv-reenlightenment", X86CPU, hyperv_features,
6663 HYPERV_FEAT_REENLIGHTENMENT, 0),
6664 DEFINE_PROP_BIT64("hv-tlbflush", X86CPU, hyperv_features,
6665 HYPERV_FEAT_TLBFLUSH, 0),
6666 DEFINE_PROP_BIT64("hv-evmcs", X86CPU, hyperv_features,
6667 HYPERV_FEAT_EVMCS, 0),
6668 DEFINE_PROP_BIT64("hv-ipi", X86CPU, hyperv_features,
6669 HYPERV_FEAT_IPI, 0),
6670 DEFINE_PROP_BIT64("hv-stimer-direct", X86CPU, hyperv_features,
6671 HYPERV_FEAT_STIMER_DIRECT, 0),
6672 DEFINE_PROP_ON_OFF_AUTO("hv-no-nonarch-coresharing", X86CPU,
6673 hyperv_no_nonarch_cs, ON_OFF_AUTO_OFF),
6674 DEFINE_PROP_BOOL("hv-passthrough", X86CPU, hyperv_passthrough, false),
6676 DEFINE_PROP_BOOL("check", X86CPU, check_cpuid, true),
6677 DEFINE_PROP_BOOL("enforce", X86CPU, enforce_cpuid, false),
6678 DEFINE_PROP_BOOL("x-force-features", X86CPU, force_features, false),
6679 DEFINE_PROP_BOOL("kvm", X86CPU, expose_kvm, true),
6680 DEFINE_PROP_UINT32("phys-bits", X86CPU, phys_bits, 0),
6681 DEFINE_PROP_BOOL("host-phys-bits", X86CPU, host_phys_bits, false),
6682 DEFINE_PROP_UINT8("host-phys-bits-limit", X86CPU, host_phys_bits_limit, 0),
6683 DEFINE_PROP_BOOL("fill-mtrr-mask", X86CPU, fill_mtrr_mask, true),
6684 DEFINE_PROP_UINT32("level-func7", X86CPU, env.cpuid_level_func7,
6685 UINT32_MAX),
6686 DEFINE_PROP_UINT32("level", X86CPU, env.cpuid_level, UINT32_MAX),
6687 DEFINE_PROP_UINT32("xlevel", X86CPU, env.cpuid_xlevel, UINT32_MAX),
6688 DEFINE_PROP_UINT32("xlevel2", X86CPU, env.cpuid_xlevel2, UINT32_MAX),
6689 DEFINE_PROP_UINT32("min-level", X86CPU, env.cpuid_min_level, 0),
6690 DEFINE_PROP_UINT32("min-xlevel", X86CPU, env.cpuid_min_xlevel, 0),
6691 DEFINE_PROP_UINT32("min-xlevel2", X86CPU, env.cpuid_min_xlevel2, 0),
6692 DEFINE_PROP_UINT64("ucode-rev", X86CPU, ucode_rev, 0),
6693 DEFINE_PROP_BOOL("full-cpuid-auto-level", X86CPU, full_cpuid_auto_level, true),
6694 DEFINE_PROP_STRING("hv-vendor-id", X86CPU, hyperv_vendor),
6695 DEFINE_PROP_BOOL("cpuid-0xb", X86CPU, enable_cpuid_0xb, true),
6696 DEFINE_PROP_BOOL("x-vendor-cpuid-only", X86CPU, vendor_cpuid_only, true),
6697 DEFINE_PROP_BOOL("lmce", X86CPU, enable_lmce, false),
6698 DEFINE_PROP_BOOL("l3-cache", X86CPU, enable_l3_cache, true),
6699 DEFINE_PROP_BOOL("kvm-no-smi-migration", X86CPU, kvm_no_smi_migration,
6700 false),
6701 DEFINE_PROP_BOOL("vmware-cpuid-freq", X86CPU, vmware_cpuid_freq, true),
6702 DEFINE_PROP_BOOL("tcg-cpuid", X86CPU, expose_tcg, true),
6703 DEFINE_PROP_BOOL("x-migrate-smi-count", X86CPU, migrate_smi_count,
6704 true),
6706 * lecacy_cache defaults to true unless the CPU model provides its
6707 * own cache information (see x86_cpu_load_def()).
6709 DEFINE_PROP_BOOL("legacy-cache", X86CPU, legacy_cache, true),
6712 * From "Requirements for Implementing the Microsoft
6713 * Hypervisor Interface":
6714 * https://docs.microsoft.com/en-us/virtualization/hyper-v-on-windows/reference/tlfs
6716 * "Starting with Windows Server 2012 and Windows 8, if
6717 * CPUID.40000005.EAX contains a value of -1, Windows assumes that
6718 * the hypervisor imposes no specific limit to the number of VPs.
6719 * In this case, Windows Server 2012 guest VMs may use more than
6720 * 64 VPs, up to the maximum supported number of processors applicable
6721 * to the specific Windows version being used."
6723 DEFINE_PROP_INT32("x-hv-max-vps", X86CPU, hv_max_vps, -1),
6724 DEFINE_PROP_BOOL("x-hv-synic-kvm-only", X86CPU, hyperv_synic_kvm_only,
6725 false),
6726 DEFINE_PROP_BOOL("x-intel-pt-auto-level", X86CPU, intel_pt_auto_level,
6727 true),
6728 DEFINE_PROP_END_OF_LIST()
6731 #ifndef CONFIG_USER_ONLY
6732 #include "hw/core/sysemu-cpu-ops.h"
6734 static const struct SysemuCPUOps i386_sysemu_ops = {
6735 .get_memory_mapping = x86_cpu_get_memory_mapping,
6736 .get_paging_enabled = x86_cpu_get_paging_enabled,
6737 .get_phys_page_attrs_debug = x86_cpu_get_phys_page_attrs_debug,
6738 .asidx_from_attrs = x86_asidx_from_attrs,
6739 .get_crash_info = x86_cpu_get_crash_info,
6740 .write_elf32_note = x86_cpu_write_elf32_note,
6741 .write_elf64_note = x86_cpu_write_elf64_note,
6742 .write_elf32_qemunote = x86_cpu_write_elf32_qemunote,
6743 .write_elf64_qemunote = x86_cpu_write_elf64_qemunote,
6744 .legacy_vmsd = &vmstate_x86_cpu,
6746 #endif
6748 static void x86_cpu_common_class_init(ObjectClass *oc, void *data)
6750 X86CPUClass *xcc = X86_CPU_CLASS(oc);
6751 CPUClass *cc = CPU_CLASS(oc);
6752 DeviceClass *dc = DEVICE_CLASS(oc);
6753 FeatureWord w;
6755 device_class_set_parent_realize(dc, x86_cpu_realizefn,
6756 &xcc->parent_realize);
6757 device_class_set_parent_unrealize(dc, x86_cpu_unrealizefn,
6758 &xcc->parent_unrealize);
6759 device_class_set_props(dc, x86_cpu_properties);
6761 device_class_set_parent_reset(dc, x86_cpu_reset, &xcc->parent_reset);
6762 cc->reset_dump_flags = CPU_DUMP_FPU | CPU_DUMP_CCOP;
6764 cc->class_by_name = x86_cpu_class_by_name;
6765 cc->parse_features = x86_cpu_parse_featurestr;
6766 cc->has_work = x86_cpu_has_work;
6767 cc->dump_state = x86_cpu_dump_state;
6768 cc->set_pc = x86_cpu_set_pc;
6769 cc->gdb_read_register = x86_cpu_gdb_read_register;
6770 cc->gdb_write_register = x86_cpu_gdb_write_register;
6771 cc->get_arch_id = x86_cpu_get_arch_id;
6773 #ifndef CONFIG_USER_ONLY
6774 cc->sysemu_ops = &i386_sysemu_ops;
6775 #endif /* !CONFIG_USER_ONLY */
6777 cc->gdb_arch_name = x86_gdb_arch_name;
6778 #ifdef TARGET_X86_64
6779 cc->gdb_core_xml_file = "i386-64bit.xml";
6780 cc->gdb_num_core_regs = 66;
6781 #else
6782 cc->gdb_core_xml_file = "i386-32bit.xml";
6783 cc->gdb_num_core_regs = 50;
6784 #endif
6785 cc->disas_set_info = x86_disas_set_info;
6787 dc->user_creatable = true;
6789 object_class_property_add(oc, "family", "int",
6790 x86_cpuid_version_get_family,
6791 x86_cpuid_version_set_family, NULL, NULL);
6792 object_class_property_add(oc, "model", "int",
6793 x86_cpuid_version_get_model,
6794 x86_cpuid_version_set_model, NULL, NULL);
6795 object_class_property_add(oc, "stepping", "int",
6796 x86_cpuid_version_get_stepping,
6797 x86_cpuid_version_set_stepping, NULL, NULL);
6798 object_class_property_add_str(oc, "vendor",
6799 x86_cpuid_get_vendor,
6800 x86_cpuid_set_vendor);
6801 object_class_property_add_str(oc, "model-id",
6802 x86_cpuid_get_model_id,
6803 x86_cpuid_set_model_id);
6804 object_class_property_add(oc, "tsc-frequency", "int",
6805 x86_cpuid_get_tsc_freq,
6806 x86_cpuid_set_tsc_freq, NULL, NULL);
6808 * The "unavailable-features" property has the same semantics as
6809 * CpuDefinitionInfo.unavailable-features on the "query-cpu-definitions"
6810 * QMP command: they list the features that would have prevented the
6811 * CPU from running if the "enforce" flag was set.
6813 object_class_property_add(oc, "unavailable-features", "strList",
6814 x86_cpu_get_unavailable_features,
6815 NULL, NULL, NULL);
6817 #if !defined(CONFIG_USER_ONLY)
6818 object_class_property_add(oc, "crash-information", "GuestPanicInformation",
6819 x86_cpu_get_crash_info_qom, NULL, NULL, NULL);
6820 #endif
6822 for (w = 0; w < FEATURE_WORDS; w++) {
6823 int bitnr;
6824 for (bitnr = 0; bitnr < 64; bitnr++) {
6825 x86_cpu_register_feature_bit_props(xcc, w, bitnr);
6830 static const TypeInfo x86_cpu_type_info = {
6831 .name = TYPE_X86_CPU,
6832 .parent = TYPE_CPU,
6833 .instance_size = sizeof(X86CPU),
6834 .instance_init = x86_cpu_initfn,
6835 .instance_post_init = x86_cpu_post_initfn,
6837 .abstract = true,
6838 .class_size = sizeof(X86CPUClass),
6839 .class_init = x86_cpu_common_class_init,
6843 /* "base" CPU model, used by query-cpu-model-expansion */
6844 static void x86_cpu_base_class_init(ObjectClass *oc, void *data)
6846 X86CPUClass *xcc = X86_CPU_CLASS(oc);
6848 xcc->static_model = true;
6849 xcc->migration_safe = true;
6850 xcc->model_description = "base CPU model type with no features enabled";
6851 xcc->ordering = 8;
6854 static const TypeInfo x86_base_cpu_type_info = {
6855 .name = X86_CPU_TYPE_NAME("base"),
6856 .parent = TYPE_X86_CPU,
6857 .class_init = x86_cpu_base_class_init,
6860 static void x86_cpu_register_types(void)
6862 int i;
6864 type_register_static(&x86_cpu_type_info);
6865 for (i = 0; i < ARRAY_SIZE(builtin_x86_defs); i++) {
6866 x86_register_cpudef_types(&builtin_x86_defs[i]);
6868 type_register_static(&max_x86_cpu_type_info);
6869 type_register_static(&x86_base_cpu_type_info);
6872 type_init(x86_cpu_register_types)