hw/timer/sse-timer: Model the SSE Subsystem System Timer
[qemu/ar7.git] / target / i386 / cpu.c
blob50008431c3562ac7522fae4e92ed40daa93b6116
1 /*
2 * i386 CPUID helper functions
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/bitops.h"
24 #include "qemu/qemu-print.h"
26 #include "cpu.h"
27 #include "tcg/tcg-cpu.h"
28 #include "tcg/helper-tcg.h"
29 #include "exec/exec-all.h"
30 #include "sysemu/kvm.h"
31 #include "sysemu/reset.h"
32 #include "sysemu/hvf.h"
33 #include "sysemu/cpus.h"
34 #include "sysemu/xen.h"
35 #include "sysemu/whpx.h"
36 #include "kvm/kvm_i386.h"
37 #include "sev_i386.h"
39 #include "qemu/error-report.h"
40 #include "qemu/module.h"
41 #include "qemu/option.h"
42 #include "qemu/config-file.h"
43 #include "qapi/error.h"
44 #include "qapi/qapi-visit-machine.h"
45 #include "qapi/qapi-visit-run-state.h"
46 #include "qapi/qmp/qdict.h"
47 #include "qapi/qmp/qerror.h"
48 #include "qapi/visitor.h"
49 #include "qom/qom-qobject.h"
50 #include "sysemu/arch_init.h"
51 #include "qapi/qapi-commands-machine-target.h"
53 #include "standard-headers/asm-x86/kvm_para.h"
55 #include "sysemu/sysemu.h"
56 #include "sysemu/tcg.h"
57 #include "hw/qdev-properties.h"
58 #include "hw/i386/topology.h"
59 #ifndef CONFIG_USER_ONLY
60 #include "exec/address-spaces.h"
61 #include "hw/i386/apic_internal.h"
62 #include "hw/boards.h"
63 #endif
65 #include "disas/capstone.h"
67 /* Helpers for building CPUID[2] descriptors: */
69 struct CPUID2CacheDescriptorInfo {
70 enum CacheType type;
71 int level;
72 int size;
73 int line_size;
74 int associativity;
78 * Known CPUID 2 cache descriptors.
79 * From Intel SDM Volume 2A, CPUID instruction
81 struct CPUID2CacheDescriptorInfo cpuid2_cache_descriptors[] = {
82 [0x06] = { .level = 1, .type = INSTRUCTION_CACHE, .size = 8 * KiB,
83 .associativity = 4, .line_size = 32, },
84 [0x08] = { .level = 1, .type = INSTRUCTION_CACHE, .size = 16 * KiB,
85 .associativity = 4, .line_size = 32, },
86 [0x09] = { .level = 1, .type = INSTRUCTION_CACHE, .size = 32 * KiB,
87 .associativity = 4, .line_size = 64, },
88 [0x0A] = { .level = 1, .type = DATA_CACHE, .size = 8 * KiB,
89 .associativity = 2, .line_size = 32, },
90 [0x0C] = { .level = 1, .type = DATA_CACHE, .size = 16 * KiB,
91 .associativity = 4, .line_size = 32, },
92 [0x0D] = { .level = 1, .type = DATA_CACHE, .size = 16 * KiB,
93 .associativity = 4, .line_size = 64, },
94 [0x0E] = { .level = 1, .type = DATA_CACHE, .size = 24 * KiB,
95 .associativity = 6, .line_size = 64, },
96 [0x1D] = { .level = 2, .type = UNIFIED_CACHE, .size = 128 * KiB,
97 .associativity = 2, .line_size = 64, },
98 [0x21] = { .level = 2, .type = UNIFIED_CACHE, .size = 256 * KiB,
99 .associativity = 8, .line_size = 64, },
100 /* lines per sector is not supported cpuid2_cache_descriptor(),
101 * so descriptors 0x22, 0x23 are not included
103 [0x24] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
104 .associativity = 16, .line_size = 64, },
105 /* lines per sector is not supported cpuid2_cache_descriptor(),
106 * so descriptors 0x25, 0x20 are not included
108 [0x2C] = { .level = 1, .type = DATA_CACHE, .size = 32 * KiB,
109 .associativity = 8, .line_size = 64, },
110 [0x30] = { .level = 1, .type = INSTRUCTION_CACHE, .size = 32 * KiB,
111 .associativity = 8, .line_size = 64, },
112 [0x41] = { .level = 2, .type = UNIFIED_CACHE, .size = 128 * KiB,
113 .associativity = 4, .line_size = 32, },
114 [0x42] = { .level = 2, .type = UNIFIED_CACHE, .size = 256 * KiB,
115 .associativity = 4, .line_size = 32, },
116 [0x43] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
117 .associativity = 4, .line_size = 32, },
118 [0x44] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
119 .associativity = 4, .line_size = 32, },
120 [0x45] = { .level = 2, .type = UNIFIED_CACHE, .size = 2 * MiB,
121 .associativity = 4, .line_size = 32, },
122 [0x46] = { .level = 3, .type = UNIFIED_CACHE, .size = 4 * MiB,
123 .associativity = 4, .line_size = 64, },
124 [0x47] = { .level = 3, .type = UNIFIED_CACHE, .size = 8 * MiB,
125 .associativity = 8, .line_size = 64, },
126 [0x48] = { .level = 2, .type = UNIFIED_CACHE, .size = 3 * MiB,
127 .associativity = 12, .line_size = 64, },
128 /* Descriptor 0x49 depends on CPU family/model, so it is not included */
129 [0x4A] = { .level = 3, .type = UNIFIED_CACHE, .size = 6 * MiB,
130 .associativity = 12, .line_size = 64, },
131 [0x4B] = { .level = 3, .type = UNIFIED_CACHE, .size = 8 * MiB,
132 .associativity = 16, .line_size = 64, },
133 [0x4C] = { .level = 3, .type = UNIFIED_CACHE, .size = 12 * MiB,
134 .associativity = 12, .line_size = 64, },
135 [0x4D] = { .level = 3, .type = UNIFIED_CACHE, .size = 16 * MiB,
136 .associativity = 16, .line_size = 64, },
137 [0x4E] = { .level = 2, .type = UNIFIED_CACHE, .size = 6 * MiB,
138 .associativity = 24, .line_size = 64, },
139 [0x60] = { .level = 1, .type = DATA_CACHE, .size = 16 * KiB,
140 .associativity = 8, .line_size = 64, },
141 [0x66] = { .level = 1, .type = DATA_CACHE, .size = 8 * KiB,
142 .associativity = 4, .line_size = 64, },
143 [0x67] = { .level = 1, .type = DATA_CACHE, .size = 16 * KiB,
144 .associativity = 4, .line_size = 64, },
145 [0x68] = { .level = 1, .type = DATA_CACHE, .size = 32 * KiB,
146 .associativity = 4, .line_size = 64, },
147 [0x78] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
148 .associativity = 4, .line_size = 64, },
149 /* lines per sector is not supported cpuid2_cache_descriptor(),
150 * so descriptors 0x79, 0x7A, 0x7B, 0x7C are not included.
152 [0x7D] = { .level = 2, .type = UNIFIED_CACHE, .size = 2 * MiB,
153 .associativity = 8, .line_size = 64, },
154 [0x7F] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
155 .associativity = 2, .line_size = 64, },
156 [0x80] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
157 .associativity = 8, .line_size = 64, },
158 [0x82] = { .level = 2, .type = UNIFIED_CACHE, .size = 256 * KiB,
159 .associativity = 8, .line_size = 32, },
160 [0x83] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
161 .associativity = 8, .line_size = 32, },
162 [0x84] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
163 .associativity = 8, .line_size = 32, },
164 [0x85] = { .level = 2, .type = UNIFIED_CACHE, .size = 2 * MiB,
165 .associativity = 8, .line_size = 32, },
166 [0x86] = { .level = 2, .type = UNIFIED_CACHE, .size = 512 * KiB,
167 .associativity = 4, .line_size = 64, },
168 [0x87] = { .level = 2, .type = UNIFIED_CACHE, .size = 1 * MiB,
169 .associativity = 8, .line_size = 64, },
170 [0xD0] = { .level = 3, .type = UNIFIED_CACHE, .size = 512 * KiB,
171 .associativity = 4, .line_size = 64, },
172 [0xD1] = { .level = 3, .type = UNIFIED_CACHE, .size = 1 * MiB,
173 .associativity = 4, .line_size = 64, },
174 [0xD2] = { .level = 3, .type = UNIFIED_CACHE, .size = 2 * MiB,
175 .associativity = 4, .line_size = 64, },
176 [0xD6] = { .level = 3, .type = UNIFIED_CACHE, .size = 1 * MiB,
177 .associativity = 8, .line_size = 64, },
178 [0xD7] = { .level = 3, .type = UNIFIED_CACHE, .size = 2 * MiB,
179 .associativity = 8, .line_size = 64, },
180 [0xD8] = { .level = 3, .type = UNIFIED_CACHE, .size = 4 * MiB,
181 .associativity = 8, .line_size = 64, },
182 [0xDC] = { .level = 3, .type = UNIFIED_CACHE, .size = 1.5 * MiB,
183 .associativity = 12, .line_size = 64, },
184 [0xDD] = { .level = 3, .type = UNIFIED_CACHE, .size = 3 * MiB,
185 .associativity = 12, .line_size = 64, },
186 [0xDE] = { .level = 3, .type = UNIFIED_CACHE, .size = 6 * MiB,
187 .associativity = 12, .line_size = 64, },
188 [0xE2] = { .level = 3, .type = UNIFIED_CACHE, .size = 2 * MiB,
189 .associativity = 16, .line_size = 64, },
190 [0xE3] = { .level = 3, .type = UNIFIED_CACHE, .size = 4 * MiB,
191 .associativity = 16, .line_size = 64, },
192 [0xE4] = { .level = 3, .type = UNIFIED_CACHE, .size = 8 * MiB,
193 .associativity = 16, .line_size = 64, },
194 [0xEA] = { .level = 3, .type = UNIFIED_CACHE, .size = 12 * MiB,
195 .associativity = 24, .line_size = 64, },
196 [0xEB] = { .level = 3, .type = UNIFIED_CACHE, .size = 18 * MiB,
197 .associativity = 24, .line_size = 64, },
198 [0xEC] = { .level = 3, .type = UNIFIED_CACHE, .size = 24 * MiB,
199 .associativity = 24, .line_size = 64, },
203 * "CPUID leaf 2 does not report cache descriptor information,
204 * use CPUID leaf 4 to query cache parameters"
206 #define CACHE_DESCRIPTOR_UNAVAILABLE 0xFF
209 * Return a CPUID 2 cache descriptor for a given cache.
210 * If no known descriptor is found, return CACHE_DESCRIPTOR_UNAVAILABLE
212 static uint8_t cpuid2_cache_descriptor(CPUCacheInfo *cache)
214 int i;
216 assert(cache->size > 0);
217 assert(cache->level > 0);
218 assert(cache->line_size > 0);
219 assert(cache->associativity > 0);
220 for (i = 0; i < ARRAY_SIZE(cpuid2_cache_descriptors); i++) {
221 struct CPUID2CacheDescriptorInfo *d = &cpuid2_cache_descriptors[i];
222 if (d->level == cache->level && d->type == cache->type &&
223 d->size == cache->size && d->line_size == cache->line_size &&
224 d->associativity == cache->associativity) {
225 return i;
229 return CACHE_DESCRIPTOR_UNAVAILABLE;
232 /* CPUID Leaf 4 constants: */
234 /* EAX: */
235 #define CACHE_TYPE_D 1
236 #define CACHE_TYPE_I 2
237 #define CACHE_TYPE_UNIFIED 3
239 #define CACHE_LEVEL(l) (l << 5)
241 #define CACHE_SELF_INIT_LEVEL (1 << 8)
243 /* EDX: */
244 #define CACHE_NO_INVD_SHARING (1 << 0)
245 #define CACHE_INCLUSIVE (1 << 1)
246 #define CACHE_COMPLEX_IDX (1 << 2)
248 /* Encode CacheType for CPUID[4].EAX */
249 #define CACHE_TYPE(t) (((t) == DATA_CACHE) ? CACHE_TYPE_D : \
250 ((t) == INSTRUCTION_CACHE) ? CACHE_TYPE_I : \
251 ((t) == UNIFIED_CACHE) ? CACHE_TYPE_UNIFIED : \
252 0 /* Invalid value */)
255 /* Encode cache info for CPUID[4] */
256 static void encode_cache_cpuid4(CPUCacheInfo *cache,
257 int num_apic_ids, int num_cores,
258 uint32_t *eax, uint32_t *ebx,
259 uint32_t *ecx, uint32_t *edx)
261 assert(cache->size == cache->line_size * cache->associativity *
262 cache->partitions * cache->sets);
264 assert(num_apic_ids > 0);
265 *eax = CACHE_TYPE(cache->type) |
266 CACHE_LEVEL(cache->level) |
267 (cache->self_init ? CACHE_SELF_INIT_LEVEL : 0) |
268 ((num_cores - 1) << 26) |
269 ((num_apic_ids - 1) << 14);
271 assert(cache->line_size > 0);
272 assert(cache->partitions > 0);
273 assert(cache->associativity > 0);
274 /* We don't implement fully-associative caches */
275 assert(cache->associativity < cache->sets);
276 *ebx = (cache->line_size - 1) |
277 ((cache->partitions - 1) << 12) |
278 ((cache->associativity - 1) << 22);
280 assert(cache->sets > 0);
281 *ecx = cache->sets - 1;
283 *edx = (cache->no_invd_sharing ? CACHE_NO_INVD_SHARING : 0) |
284 (cache->inclusive ? CACHE_INCLUSIVE : 0) |
285 (cache->complex_indexing ? CACHE_COMPLEX_IDX : 0);
288 /* Encode cache info for CPUID[0x80000005].ECX or CPUID[0x80000005].EDX */
289 static uint32_t encode_cache_cpuid80000005(CPUCacheInfo *cache)
291 assert(cache->size % 1024 == 0);
292 assert(cache->lines_per_tag > 0);
293 assert(cache->associativity > 0);
294 assert(cache->line_size > 0);
295 return ((cache->size / 1024) << 24) | (cache->associativity << 16) |
296 (cache->lines_per_tag << 8) | (cache->line_size);
299 #define ASSOC_FULL 0xFF
301 /* AMD associativity encoding used on CPUID Leaf 0x80000006: */
302 #define AMD_ENC_ASSOC(a) (a <= 1 ? a : \
303 a == 2 ? 0x2 : \
304 a == 4 ? 0x4 : \
305 a == 8 ? 0x6 : \
306 a == 16 ? 0x8 : \
307 a == 32 ? 0xA : \
308 a == 48 ? 0xB : \
309 a == 64 ? 0xC : \
310 a == 96 ? 0xD : \
311 a == 128 ? 0xE : \
312 a == ASSOC_FULL ? 0xF : \
313 0 /* invalid value */)
316 * Encode cache info for CPUID[0x80000006].ECX and CPUID[0x80000006].EDX
317 * @l3 can be NULL.
319 static void encode_cache_cpuid80000006(CPUCacheInfo *l2,
320 CPUCacheInfo *l3,
321 uint32_t *ecx, uint32_t *edx)
323 assert(l2->size % 1024 == 0);
324 assert(l2->associativity > 0);
325 assert(l2->lines_per_tag > 0);
326 assert(l2->line_size > 0);
327 *ecx = ((l2->size / 1024) << 16) |
328 (AMD_ENC_ASSOC(l2->associativity) << 12) |
329 (l2->lines_per_tag << 8) | (l2->line_size);
331 if (l3) {
332 assert(l3->size % (512 * 1024) == 0);
333 assert(l3->associativity > 0);
334 assert(l3->lines_per_tag > 0);
335 assert(l3->line_size > 0);
336 *edx = ((l3->size / (512 * 1024)) << 18) |
337 (AMD_ENC_ASSOC(l3->associativity) << 12) |
338 (l3->lines_per_tag << 8) | (l3->line_size);
339 } else {
340 *edx = 0;
344 /* Encode cache info for CPUID[8000001D] */
345 static void encode_cache_cpuid8000001d(CPUCacheInfo *cache,
346 X86CPUTopoInfo *topo_info,
347 uint32_t *eax, uint32_t *ebx,
348 uint32_t *ecx, uint32_t *edx)
350 uint32_t l3_threads;
351 assert(cache->size == cache->line_size * cache->associativity *
352 cache->partitions * cache->sets);
354 *eax = CACHE_TYPE(cache->type) | CACHE_LEVEL(cache->level) |
355 (cache->self_init ? CACHE_SELF_INIT_LEVEL : 0);
357 /* L3 is shared among multiple cores */
358 if (cache->level == 3) {
359 l3_threads = topo_info->cores_per_die * topo_info->threads_per_core;
360 *eax |= (l3_threads - 1) << 14;
361 } else {
362 *eax |= ((topo_info->threads_per_core - 1) << 14);
365 assert(cache->line_size > 0);
366 assert(cache->partitions > 0);
367 assert(cache->associativity > 0);
368 /* We don't implement fully-associative caches */
369 assert(cache->associativity < cache->sets);
370 *ebx = (cache->line_size - 1) |
371 ((cache->partitions - 1) << 12) |
372 ((cache->associativity - 1) << 22);
374 assert(cache->sets > 0);
375 *ecx = cache->sets - 1;
377 *edx = (cache->no_invd_sharing ? CACHE_NO_INVD_SHARING : 0) |
378 (cache->inclusive ? CACHE_INCLUSIVE : 0) |
379 (cache->complex_indexing ? CACHE_COMPLEX_IDX : 0);
382 /* Encode cache info for CPUID[8000001E] */
383 static void encode_topo_cpuid8000001e(X86CPU *cpu, X86CPUTopoInfo *topo_info,
384 uint32_t *eax, uint32_t *ebx,
385 uint32_t *ecx, uint32_t *edx)
387 X86CPUTopoIDs topo_ids;
389 x86_topo_ids_from_apicid(cpu->apic_id, topo_info, &topo_ids);
391 *eax = cpu->apic_id;
394 * CPUID_Fn8000001E_EBX [Core Identifiers] (CoreId)
395 * Read-only. Reset: 0000_XXXXh.
396 * See Core::X86::Cpuid::ExtApicId.
397 * Core::X86::Cpuid::CoreId_lthree[1:0]_core[3:0]_thread[1:0];
398 * Bits Description
399 * 31:16 Reserved.
400 * 15:8 ThreadsPerCore: threads per core. Read-only. Reset: XXh.
401 * The number of threads per core is ThreadsPerCore+1.
402 * 7:0 CoreId: core ID. Read-only. Reset: XXh.
404 * NOTE: CoreId is already part of apic_id. Just use it. We can
405 * use all the 8 bits to represent the core_id here.
407 *ebx = ((topo_info->threads_per_core - 1) << 8) | (topo_ids.core_id & 0xFF);
410 * CPUID_Fn8000001E_ECX [Node Identifiers] (NodeId)
411 * Read-only. Reset: 0000_0XXXh.
412 * Core::X86::Cpuid::NodeId_lthree[1:0]_core[3:0]_thread[1:0];
413 * Bits Description
414 * 31:11 Reserved.
415 * 10:8 NodesPerProcessor: Node per processor. Read-only. Reset: XXXb.
416 * ValidValues:
417 * Value Description
418 * 000b 1 node per processor.
419 * 001b 2 nodes per processor.
420 * 010b Reserved.
421 * 011b 4 nodes per processor.
422 * 111b-100b Reserved.
423 * 7:0 NodeId: Node ID. Read-only. Reset: XXh.
425 * NOTE: Hardware reserves 3 bits for number of nodes per processor.
426 * But users can create more nodes than the actual hardware can
427 * support. To genaralize we can use all the upper 8 bits for nodes.
428 * NodeId is combination of node and socket_id which is already decoded
429 * in apic_id. Just use it by shifting.
431 *ecx = ((topo_info->dies_per_pkg - 1) << 8) |
432 ((cpu->apic_id >> apicid_die_offset(topo_info)) & 0xFF);
434 *edx = 0;
438 * Definitions of the hardcoded cache entries we expose:
439 * These are legacy cache values. If there is a need to change any
440 * of these values please use builtin_x86_defs
443 /* L1 data cache: */
444 static CPUCacheInfo legacy_l1d_cache = {
445 .type = DATA_CACHE,
446 .level = 1,
447 .size = 32 * KiB,
448 .self_init = 1,
449 .line_size = 64,
450 .associativity = 8,
451 .sets = 64,
452 .partitions = 1,
453 .no_invd_sharing = true,
456 /*FIXME: CPUID leaf 0x80000005 is inconsistent with leaves 2 & 4 */
457 static CPUCacheInfo legacy_l1d_cache_amd = {
458 .type = DATA_CACHE,
459 .level = 1,
460 .size = 64 * KiB,
461 .self_init = 1,
462 .line_size = 64,
463 .associativity = 2,
464 .sets = 512,
465 .partitions = 1,
466 .lines_per_tag = 1,
467 .no_invd_sharing = true,
470 /* L1 instruction cache: */
471 static CPUCacheInfo legacy_l1i_cache = {
472 .type = INSTRUCTION_CACHE,
473 .level = 1,
474 .size = 32 * KiB,
475 .self_init = 1,
476 .line_size = 64,
477 .associativity = 8,
478 .sets = 64,
479 .partitions = 1,
480 .no_invd_sharing = true,
483 /*FIXME: CPUID leaf 0x80000005 is inconsistent with leaves 2 & 4 */
484 static CPUCacheInfo legacy_l1i_cache_amd = {
485 .type = INSTRUCTION_CACHE,
486 .level = 1,
487 .size = 64 * KiB,
488 .self_init = 1,
489 .line_size = 64,
490 .associativity = 2,
491 .sets = 512,
492 .partitions = 1,
493 .lines_per_tag = 1,
494 .no_invd_sharing = true,
497 /* Level 2 unified cache: */
498 static CPUCacheInfo legacy_l2_cache = {
499 .type = UNIFIED_CACHE,
500 .level = 2,
501 .size = 4 * MiB,
502 .self_init = 1,
503 .line_size = 64,
504 .associativity = 16,
505 .sets = 4096,
506 .partitions = 1,
507 .no_invd_sharing = true,
510 /*FIXME: CPUID leaf 2 descriptor is inconsistent with CPUID leaf 4 */
511 static CPUCacheInfo legacy_l2_cache_cpuid2 = {
512 .type = UNIFIED_CACHE,
513 .level = 2,
514 .size = 2 * MiB,
515 .line_size = 64,
516 .associativity = 8,
520 /*FIXME: CPUID leaf 0x80000006 is inconsistent with leaves 2 & 4 */
521 static CPUCacheInfo legacy_l2_cache_amd = {
522 .type = UNIFIED_CACHE,
523 .level = 2,
524 .size = 512 * KiB,
525 .line_size = 64,
526 .lines_per_tag = 1,
527 .associativity = 16,
528 .sets = 512,
529 .partitions = 1,
532 /* Level 3 unified cache: */
533 static CPUCacheInfo legacy_l3_cache = {
534 .type = UNIFIED_CACHE,
535 .level = 3,
536 .size = 16 * MiB,
537 .line_size = 64,
538 .associativity = 16,
539 .sets = 16384,
540 .partitions = 1,
541 .lines_per_tag = 1,
542 .self_init = true,
543 .inclusive = true,
544 .complex_indexing = true,
547 /* TLB definitions: */
549 #define L1_DTLB_2M_ASSOC 1
550 #define L1_DTLB_2M_ENTRIES 255
551 #define L1_DTLB_4K_ASSOC 1
552 #define L1_DTLB_4K_ENTRIES 255
554 #define L1_ITLB_2M_ASSOC 1
555 #define L1_ITLB_2M_ENTRIES 255
556 #define L1_ITLB_4K_ASSOC 1
557 #define L1_ITLB_4K_ENTRIES 255
559 #define L2_DTLB_2M_ASSOC 0 /* disabled */
560 #define L2_DTLB_2M_ENTRIES 0 /* disabled */
561 #define L2_DTLB_4K_ASSOC 4
562 #define L2_DTLB_4K_ENTRIES 512
564 #define L2_ITLB_2M_ASSOC 0 /* disabled */
565 #define L2_ITLB_2M_ENTRIES 0 /* disabled */
566 #define L2_ITLB_4K_ASSOC 4
567 #define L2_ITLB_4K_ENTRIES 512
569 /* CPUID Leaf 0x14 constants: */
570 #define INTEL_PT_MAX_SUBLEAF 0x1
572 * bit[00]: IA32_RTIT_CTL.CR3 filter can be set to 1 and IA32_RTIT_CR3_MATCH
573 * MSR can be accessed;
574 * bit[01]: Support Configurable PSB and Cycle-Accurate Mode;
575 * bit[02]: Support IP Filtering, TraceStop filtering, and preservation
576 * of Intel PT MSRs across warm reset;
577 * bit[03]: Support MTC timing packet and suppression of COFI-based packets;
579 #define INTEL_PT_MINIMAL_EBX 0xf
581 * bit[00]: Tracing can be enabled with IA32_RTIT_CTL.ToPA = 1 and
582 * IA32_RTIT_OUTPUT_BASE and IA32_RTIT_OUTPUT_MASK_PTRS MSRs can be
583 * accessed;
584 * bit[01]: ToPA tables can hold any number of output entries, up to the
585 * maximum allowed by the MaskOrTableOffset field of
586 * IA32_RTIT_OUTPUT_MASK_PTRS;
587 * bit[02]: Support Single-Range Output scheme;
589 #define INTEL_PT_MINIMAL_ECX 0x7
590 /* generated packets which contain IP payloads have LIP values */
591 #define INTEL_PT_IP_LIP (1 << 31)
592 #define INTEL_PT_ADDR_RANGES_NUM 0x2 /* Number of configurable address ranges */
593 #define INTEL_PT_ADDR_RANGES_NUM_MASK 0x3
594 #define INTEL_PT_MTC_BITMAP (0x0249 << 16) /* Support ART(0,3,6,9) */
595 #define INTEL_PT_CYCLE_BITMAP 0x1fff /* Support 0,2^(0~11) */
596 #define INTEL_PT_PSB_BITMAP (0x003f << 16) /* Support 2K,4K,8K,16K,32K,64K */
598 static void x86_cpu_vendor_words2str(char *dst, uint32_t vendor1,
599 uint32_t vendor2, uint32_t vendor3)
601 int i;
602 for (i = 0; i < 4; i++) {
603 dst[i] = vendor1 >> (8 * i);
604 dst[i + 4] = vendor2 >> (8 * i);
605 dst[i + 8] = vendor3 >> (8 * i);
607 dst[CPUID_VENDOR_SZ] = '\0';
610 #define I486_FEATURES (CPUID_FP87 | CPUID_VME | CPUID_PSE)
611 #define PENTIUM_FEATURES (I486_FEATURES | CPUID_DE | CPUID_TSC | \
612 CPUID_MSR | CPUID_MCE | CPUID_CX8 | CPUID_MMX | CPUID_APIC)
613 #define PENTIUM2_FEATURES (PENTIUM_FEATURES | CPUID_PAE | CPUID_SEP | \
614 CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV | CPUID_PAT | \
615 CPUID_PSE36 | CPUID_FXSR)
616 #define PENTIUM3_FEATURES (PENTIUM2_FEATURES | CPUID_SSE)
617 #define PPRO_FEATURES (CPUID_FP87 | CPUID_DE | CPUID_PSE | CPUID_TSC | \
618 CPUID_MSR | CPUID_MCE | CPUID_CX8 | CPUID_PGE | CPUID_CMOV | \
619 CPUID_PAT | CPUID_FXSR | CPUID_MMX | CPUID_SSE | CPUID_SSE2 | \
620 CPUID_PAE | CPUID_SEP | CPUID_APIC)
622 #define TCG_FEATURES (CPUID_FP87 | CPUID_PSE | CPUID_TSC | CPUID_MSR | \
623 CPUID_PAE | CPUID_MCE | CPUID_CX8 | CPUID_APIC | CPUID_SEP | \
624 CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV | CPUID_PAT | \
625 CPUID_PSE36 | CPUID_CLFLUSH | CPUID_ACPI | CPUID_MMX | \
626 CPUID_FXSR | CPUID_SSE | CPUID_SSE2 | CPUID_SS | CPUID_DE)
627 /* partly implemented:
628 CPUID_MTRR, CPUID_MCA, CPUID_CLFLUSH (needed for Win64) */
629 /* missing:
630 CPUID_VME, CPUID_DTS, CPUID_SS, CPUID_HT, CPUID_TM, CPUID_PBE */
631 #define TCG_EXT_FEATURES (CPUID_EXT_SSE3 | CPUID_EXT_PCLMULQDQ | \
632 CPUID_EXT_MONITOR | CPUID_EXT_SSSE3 | CPUID_EXT_CX16 | \
633 CPUID_EXT_SSE41 | CPUID_EXT_SSE42 | CPUID_EXT_POPCNT | \
634 CPUID_EXT_XSAVE | /* CPUID_EXT_OSXSAVE is dynamic */ \
635 CPUID_EXT_MOVBE | CPUID_EXT_AES | CPUID_EXT_HYPERVISOR | \
636 CPUID_EXT_RDRAND)
637 /* missing:
638 CPUID_EXT_DTES64, CPUID_EXT_DSCPL, CPUID_EXT_VMX, CPUID_EXT_SMX,
639 CPUID_EXT_EST, CPUID_EXT_TM2, CPUID_EXT_CID, CPUID_EXT_FMA,
640 CPUID_EXT_XTPR, CPUID_EXT_PDCM, CPUID_EXT_PCID, CPUID_EXT_DCA,
641 CPUID_EXT_X2APIC, CPUID_EXT_TSC_DEADLINE_TIMER, CPUID_EXT_AVX,
642 CPUID_EXT_F16C */
644 #ifdef TARGET_X86_64
645 #define TCG_EXT2_X86_64_FEATURES (CPUID_EXT2_SYSCALL | CPUID_EXT2_LM)
646 #else
647 #define TCG_EXT2_X86_64_FEATURES 0
648 #endif
650 #define TCG_EXT2_FEATURES ((TCG_FEATURES & CPUID_EXT2_AMD_ALIASES) | \
651 CPUID_EXT2_NX | CPUID_EXT2_MMXEXT | CPUID_EXT2_RDTSCP | \
652 CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT | CPUID_EXT2_PDPE1GB | \
653 TCG_EXT2_X86_64_FEATURES)
654 #define TCG_EXT3_FEATURES (CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM | \
655 CPUID_EXT3_CR8LEG | CPUID_EXT3_ABM | CPUID_EXT3_SSE4A)
656 #define TCG_EXT4_FEATURES 0
657 #define TCG_SVM_FEATURES CPUID_SVM_NPT
658 #define TCG_KVM_FEATURES 0
659 #define TCG_7_0_EBX_FEATURES (CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_SMAP | \
660 CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ADX | \
661 CPUID_7_0_EBX_PCOMMIT | CPUID_7_0_EBX_CLFLUSHOPT | \
662 CPUID_7_0_EBX_CLWB | CPUID_7_0_EBX_MPX | CPUID_7_0_EBX_FSGSBASE | \
663 CPUID_7_0_EBX_ERMS)
664 /* missing:
665 CPUID_7_0_EBX_HLE, CPUID_7_0_EBX_AVX2,
666 CPUID_7_0_EBX_INVPCID, CPUID_7_0_EBX_RTM,
667 CPUID_7_0_EBX_RDSEED */
668 #define TCG_7_0_ECX_FEATURES (CPUID_7_0_ECX_PKU | \
669 /* CPUID_7_0_ECX_OSPKE is dynamic */ \
670 CPUID_7_0_ECX_LA57 | CPUID_7_0_ECX_PKS)
671 #define TCG_7_0_EDX_FEATURES 0
672 #define TCG_7_1_EAX_FEATURES 0
673 #define TCG_APM_FEATURES 0
674 #define TCG_6_EAX_FEATURES CPUID_6_EAX_ARAT
675 #define TCG_XSAVE_FEATURES (CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XGETBV1)
676 /* missing:
677 CPUID_XSAVE_XSAVEC, CPUID_XSAVE_XSAVES */
678 #define TCG_14_0_ECX_FEATURES 0
680 typedef enum FeatureWordType {
681 CPUID_FEATURE_WORD,
682 MSR_FEATURE_WORD,
683 } FeatureWordType;
685 typedef struct FeatureWordInfo {
686 FeatureWordType type;
687 /* feature flags names are taken from "Intel Processor Identification and
688 * the CPUID Instruction" and AMD's "CPUID Specification".
689 * In cases of disagreement between feature naming conventions,
690 * aliases may be added.
692 const char *feat_names[64];
693 union {
694 /* If type==CPUID_FEATURE_WORD */
695 struct {
696 uint32_t eax; /* Input EAX for CPUID */
697 bool needs_ecx; /* CPUID instruction uses ECX as input */
698 uint32_t ecx; /* Input ECX value for CPUID */
699 int reg; /* output register (R_* constant) */
700 } cpuid;
701 /* If type==MSR_FEATURE_WORD */
702 struct {
703 uint32_t index;
704 } msr;
706 uint64_t tcg_features; /* Feature flags supported by TCG */
707 uint64_t unmigratable_flags; /* Feature flags known to be unmigratable */
708 uint64_t migratable_flags; /* Feature flags known to be migratable */
709 /* Features that shouldn't be auto-enabled by "-cpu host" */
710 uint64_t no_autoenable_flags;
711 } FeatureWordInfo;
713 static FeatureWordInfo feature_word_info[FEATURE_WORDS] = {
714 [FEAT_1_EDX] = {
715 .type = CPUID_FEATURE_WORD,
716 .feat_names = {
717 "fpu", "vme", "de", "pse",
718 "tsc", "msr", "pae", "mce",
719 "cx8", "apic", NULL, "sep",
720 "mtrr", "pge", "mca", "cmov",
721 "pat", "pse36", "pn" /* Intel psn */, "clflush" /* Intel clfsh */,
722 NULL, "ds" /* Intel dts */, "acpi", "mmx",
723 "fxsr", "sse", "sse2", "ss",
724 "ht" /* Intel htt */, "tm", "ia64", "pbe",
726 .cpuid = {.eax = 1, .reg = R_EDX, },
727 .tcg_features = TCG_FEATURES,
729 [FEAT_1_ECX] = {
730 .type = CPUID_FEATURE_WORD,
731 .feat_names = {
732 "pni" /* Intel,AMD sse3 */, "pclmulqdq", "dtes64", "monitor",
733 "ds-cpl", "vmx", "smx", "est",
734 "tm2", "ssse3", "cid", NULL,
735 "fma", "cx16", "xtpr", "pdcm",
736 NULL, "pcid", "dca", "sse4.1",
737 "sse4.2", "x2apic", "movbe", "popcnt",
738 "tsc-deadline", "aes", "xsave", NULL /* osxsave */,
739 "avx", "f16c", "rdrand", "hypervisor",
741 .cpuid = { .eax = 1, .reg = R_ECX, },
742 .tcg_features = TCG_EXT_FEATURES,
744 /* Feature names that are already defined on feature_name[] but
745 * are set on CPUID[8000_0001].EDX on AMD CPUs don't have their
746 * names on feat_names below. They are copied automatically
747 * to features[FEAT_8000_0001_EDX] if and only if CPU vendor is AMD.
749 [FEAT_8000_0001_EDX] = {
750 .type = CPUID_FEATURE_WORD,
751 .feat_names = {
752 NULL /* fpu */, NULL /* vme */, NULL /* de */, NULL /* pse */,
753 NULL /* tsc */, NULL /* msr */, NULL /* pae */, NULL /* mce */,
754 NULL /* cx8 */, NULL /* apic */, NULL, "syscall",
755 NULL /* mtrr */, NULL /* pge */, NULL /* mca */, NULL /* cmov */,
756 NULL /* pat */, NULL /* pse36 */, NULL, NULL /* Linux mp */,
757 "nx", NULL, "mmxext", NULL /* mmx */,
758 NULL /* fxsr */, "fxsr-opt", "pdpe1gb", "rdtscp",
759 NULL, "lm", "3dnowext", "3dnow",
761 .cpuid = { .eax = 0x80000001, .reg = R_EDX, },
762 .tcg_features = TCG_EXT2_FEATURES,
764 [FEAT_8000_0001_ECX] = {
765 .type = CPUID_FEATURE_WORD,
766 .feat_names = {
767 "lahf-lm", "cmp-legacy", "svm", "extapic",
768 "cr8legacy", "abm", "sse4a", "misalignsse",
769 "3dnowprefetch", "osvw", "ibs", "xop",
770 "skinit", "wdt", NULL, "lwp",
771 "fma4", "tce", NULL, "nodeid-msr",
772 NULL, "tbm", "topoext", "perfctr-core",
773 "perfctr-nb", NULL, NULL, NULL,
774 NULL, NULL, NULL, NULL,
776 .cpuid = { .eax = 0x80000001, .reg = R_ECX, },
777 .tcg_features = TCG_EXT3_FEATURES,
779 * TOPOEXT is always allowed but can't be enabled blindly by
780 * "-cpu host", as it requires consistent cache topology info
781 * to be provided so it doesn't confuse guests.
783 .no_autoenable_flags = CPUID_EXT3_TOPOEXT,
785 [FEAT_C000_0001_EDX] = {
786 .type = CPUID_FEATURE_WORD,
787 .feat_names = {
788 NULL, NULL, "xstore", "xstore-en",
789 NULL, NULL, "xcrypt", "xcrypt-en",
790 "ace2", "ace2-en", "phe", "phe-en",
791 "pmm", "pmm-en", NULL, NULL,
792 NULL, NULL, NULL, NULL,
793 NULL, NULL, NULL, NULL,
794 NULL, NULL, NULL, NULL,
795 NULL, NULL, NULL, NULL,
797 .cpuid = { .eax = 0xC0000001, .reg = R_EDX, },
798 .tcg_features = TCG_EXT4_FEATURES,
800 [FEAT_KVM] = {
801 .type = CPUID_FEATURE_WORD,
802 .feat_names = {
803 "kvmclock", "kvm-nopiodelay", "kvm-mmu", "kvmclock",
804 "kvm-asyncpf", "kvm-steal-time", "kvm-pv-eoi", "kvm-pv-unhalt",
805 NULL, "kvm-pv-tlb-flush", NULL, "kvm-pv-ipi",
806 "kvm-poll-control", "kvm-pv-sched-yield", "kvm-asyncpf-int", "kvm-msi-ext-dest-id",
807 NULL, NULL, NULL, NULL,
808 NULL, NULL, NULL, NULL,
809 "kvmclock-stable-bit", NULL, NULL, NULL,
810 NULL, NULL, NULL, NULL,
812 .cpuid = { .eax = KVM_CPUID_FEATURES, .reg = R_EAX, },
813 .tcg_features = TCG_KVM_FEATURES,
815 [FEAT_KVM_HINTS] = {
816 .type = CPUID_FEATURE_WORD,
817 .feat_names = {
818 "kvm-hint-dedicated", NULL, NULL, NULL,
819 NULL, NULL, NULL, NULL,
820 NULL, NULL, NULL, NULL,
821 NULL, NULL, NULL, NULL,
822 NULL, NULL, NULL, NULL,
823 NULL, NULL, NULL, NULL,
824 NULL, NULL, NULL, NULL,
825 NULL, NULL, NULL, NULL,
827 .cpuid = { .eax = KVM_CPUID_FEATURES, .reg = R_EDX, },
828 .tcg_features = TCG_KVM_FEATURES,
830 * KVM hints aren't auto-enabled by -cpu host, they need to be
831 * explicitly enabled in the command-line.
833 .no_autoenable_flags = ~0U,
836 * .feat_names are commented out for Hyper-V enlightenments because we
837 * don't want to have two different ways for enabling them on QEMU command
838 * line. Some features (e.g. "hyperv_time", "hyperv_vapic", ...) require
839 * enabling several feature bits simultaneously, exposing these bits
840 * individually may just confuse guests.
842 [FEAT_HYPERV_EAX] = {
843 .type = CPUID_FEATURE_WORD,
844 .feat_names = {
845 NULL /* hv_msr_vp_runtime_access */, NULL /* hv_msr_time_refcount_access */,
846 NULL /* hv_msr_synic_access */, NULL /* hv_msr_stimer_access */,
847 NULL /* hv_msr_apic_access */, NULL /* hv_msr_hypercall_access */,
848 NULL /* hv_vpindex_access */, NULL /* hv_msr_reset_access */,
849 NULL /* hv_msr_stats_access */, NULL /* hv_reftsc_access */,
850 NULL /* hv_msr_idle_access */, NULL /* hv_msr_frequency_access */,
851 NULL /* hv_msr_debug_access */, NULL /* hv_msr_reenlightenment_access */,
852 NULL, NULL,
853 NULL, NULL, NULL, NULL,
854 NULL, NULL, NULL, NULL,
855 NULL, NULL, NULL, NULL,
856 NULL, NULL, NULL, NULL,
858 .cpuid = { .eax = 0x40000003, .reg = R_EAX, },
860 [FEAT_HYPERV_EBX] = {
861 .type = CPUID_FEATURE_WORD,
862 .feat_names = {
863 NULL /* hv_create_partitions */, NULL /* hv_access_partition_id */,
864 NULL /* hv_access_memory_pool */, NULL /* hv_adjust_message_buffers */,
865 NULL /* hv_post_messages */, NULL /* hv_signal_events */,
866 NULL /* hv_create_port */, NULL /* hv_connect_port */,
867 NULL /* hv_access_stats */, NULL, NULL, NULL /* hv_debugging */,
868 NULL /* hv_cpu_power_management */, NULL /* hv_configure_profiler */,
869 NULL, NULL,
870 NULL, NULL, NULL, NULL,
871 NULL, NULL, NULL, NULL,
872 NULL, NULL, NULL, NULL,
873 NULL, NULL, NULL, NULL,
875 .cpuid = { .eax = 0x40000003, .reg = R_EBX, },
877 [FEAT_HYPERV_EDX] = {
878 .type = CPUID_FEATURE_WORD,
879 .feat_names = {
880 NULL /* hv_mwait */, NULL /* hv_guest_debugging */,
881 NULL /* hv_perf_monitor */, NULL /* hv_cpu_dynamic_part */,
882 NULL /* hv_hypercall_params_xmm */, NULL /* hv_guest_idle_state */,
883 NULL, NULL,
884 NULL, NULL, NULL /* hv_guest_crash_msr */, NULL,
885 NULL, NULL, NULL, NULL,
886 NULL, NULL, NULL, NULL,
887 NULL, NULL, NULL, NULL,
888 NULL, NULL, NULL, NULL,
889 NULL, NULL, NULL, NULL,
891 .cpuid = { .eax = 0x40000003, .reg = R_EDX, },
893 [FEAT_HV_RECOMM_EAX] = {
894 .type = CPUID_FEATURE_WORD,
895 .feat_names = {
896 NULL /* hv_recommend_pv_as_switch */,
897 NULL /* hv_recommend_pv_tlbflush_local */,
898 NULL /* hv_recommend_pv_tlbflush_remote */,
899 NULL /* hv_recommend_msr_apic_access */,
900 NULL /* hv_recommend_msr_reset */,
901 NULL /* hv_recommend_relaxed_timing */,
902 NULL /* hv_recommend_dma_remapping */,
903 NULL /* hv_recommend_int_remapping */,
904 NULL /* hv_recommend_x2apic_msrs */,
905 NULL /* hv_recommend_autoeoi_deprecation */,
906 NULL /* hv_recommend_pv_ipi */,
907 NULL /* hv_recommend_ex_hypercalls */,
908 NULL /* hv_hypervisor_is_nested */,
909 NULL /* hv_recommend_int_mbec */,
910 NULL /* hv_recommend_evmcs */,
911 NULL,
912 NULL, NULL, NULL, NULL,
913 NULL, NULL, NULL, NULL,
914 NULL, NULL, NULL, NULL,
915 NULL, NULL, NULL, NULL,
917 .cpuid = { .eax = 0x40000004, .reg = R_EAX, },
919 [FEAT_HV_NESTED_EAX] = {
920 .type = CPUID_FEATURE_WORD,
921 .cpuid = { .eax = 0x4000000A, .reg = R_EAX, },
923 [FEAT_SVM] = {
924 .type = CPUID_FEATURE_WORD,
925 .feat_names = {
926 "npt", "lbrv", "svm-lock", "nrip-save",
927 "tsc-scale", "vmcb-clean", "flushbyasid", "decodeassists",
928 NULL, NULL, "pause-filter", NULL,
929 "pfthreshold", "avic", NULL, "v-vmsave-vmload",
930 "vgif", NULL, NULL, NULL,
931 NULL, NULL, NULL, NULL,
932 NULL, NULL, NULL, NULL,
933 "svme-addr-chk", NULL, NULL, NULL,
935 .cpuid = { .eax = 0x8000000A, .reg = R_EDX, },
936 .tcg_features = TCG_SVM_FEATURES,
938 [FEAT_7_0_EBX] = {
939 .type = CPUID_FEATURE_WORD,
940 .feat_names = {
941 "fsgsbase", "tsc-adjust", NULL, "bmi1",
942 "hle", "avx2", NULL, "smep",
943 "bmi2", "erms", "invpcid", "rtm",
944 NULL, NULL, "mpx", NULL,
945 "avx512f", "avx512dq", "rdseed", "adx",
946 "smap", "avx512ifma", "pcommit", "clflushopt",
947 "clwb", "intel-pt", "avx512pf", "avx512er",
948 "avx512cd", "sha-ni", "avx512bw", "avx512vl",
950 .cpuid = {
951 .eax = 7,
952 .needs_ecx = true, .ecx = 0,
953 .reg = R_EBX,
955 .tcg_features = TCG_7_0_EBX_FEATURES,
957 [FEAT_7_0_ECX] = {
958 .type = CPUID_FEATURE_WORD,
959 .feat_names = {
960 NULL, "avx512vbmi", "umip", "pku",
961 NULL /* ospke */, "waitpkg", "avx512vbmi2", NULL,
962 "gfni", "vaes", "vpclmulqdq", "avx512vnni",
963 "avx512bitalg", NULL, "avx512-vpopcntdq", NULL,
964 "la57", NULL, NULL, NULL,
965 NULL, NULL, "rdpid", NULL,
966 "bus-lock-detect", "cldemote", NULL, "movdiri",
967 "movdir64b", NULL, NULL, "pks",
969 .cpuid = {
970 .eax = 7,
971 .needs_ecx = true, .ecx = 0,
972 .reg = R_ECX,
974 .tcg_features = TCG_7_0_ECX_FEATURES,
976 [FEAT_7_0_EDX] = {
977 .type = CPUID_FEATURE_WORD,
978 .feat_names = {
979 NULL, NULL, "avx512-4vnniw", "avx512-4fmaps",
980 "fsrm", NULL, NULL, NULL,
981 "avx512-vp2intersect", NULL, "md-clear", NULL,
982 NULL, NULL, "serialize", NULL,
983 "tsx-ldtrk", NULL, NULL /* pconfig */, NULL,
984 NULL, NULL, NULL, "avx512-fp16",
985 NULL, NULL, "spec-ctrl", "stibp",
986 NULL, "arch-capabilities", "core-capability", "ssbd",
988 .cpuid = {
989 .eax = 7,
990 .needs_ecx = true, .ecx = 0,
991 .reg = R_EDX,
993 .tcg_features = TCG_7_0_EDX_FEATURES,
995 [FEAT_7_1_EAX] = {
996 .type = CPUID_FEATURE_WORD,
997 .feat_names = {
998 NULL, NULL, NULL, NULL,
999 NULL, "avx512-bf16", NULL, NULL,
1000 NULL, NULL, NULL, NULL,
1001 NULL, NULL, NULL, NULL,
1002 NULL, NULL, NULL, NULL,
1003 NULL, NULL, NULL, NULL,
1004 NULL, NULL, NULL, NULL,
1005 NULL, NULL, NULL, NULL,
1007 .cpuid = {
1008 .eax = 7,
1009 .needs_ecx = true, .ecx = 1,
1010 .reg = R_EAX,
1012 .tcg_features = TCG_7_1_EAX_FEATURES,
1014 [FEAT_8000_0007_EDX] = {
1015 .type = CPUID_FEATURE_WORD,
1016 .feat_names = {
1017 NULL, NULL, NULL, NULL,
1018 NULL, NULL, NULL, NULL,
1019 "invtsc", NULL, NULL, NULL,
1020 NULL, NULL, NULL, NULL,
1021 NULL, NULL, NULL, NULL,
1022 NULL, NULL, NULL, NULL,
1023 NULL, NULL, NULL, NULL,
1024 NULL, NULL, NULL, NULL,
1026 .cpuid = { .eax = 0x80000007, .reg = R_EDX, },
1027 .tcg_features = TCG_APM_FEATURES,
1028 .unmigratable_flags = CPUID_APM_INVTSC,
1030 [FEAT_8000_0008_EBX] = {
1031 .type = CPUID_FEATURE_WORD,
1032 .feat_names = {
1033 "clzero", NULL, "xsaveerptr", NULL,
1034 NULL, NULL, NULL, NULL,
1035 NULL, "wbnoinvd", NULL, NULL,
1036 "ibpb", NULL, "ibrs", "amd-stibp",
1037 NULL, NULL, NULL, NULL,
1038 NULL, NULL, NULL, NULL,
1039 "amd-ssbd", "virt-ssbd", "amd-no-ssb", NULL,
1040 NULL, NULL, NULL, NULL,
1042 .cpuid = { .eax = 0x80000008, .reg = R_EBX, },
1043 .tcg_features = 0,
1044 .unmigratable_flags = 0,
1046 [FEAT_XSAVE] = {
1047 .type = CPUID_FEATURE_WORD,
1048 .feat_names = {
1049 "xsaveopt", "xsavec", "xgetbv1", "xsaves",
1050 NULL, NULL, NULL, NULL,
1051 NULL, NULL, NULL, NULL,
1052 NULL, NULL, NULL, NULL,
1053 NULL, NULL, NULL, NULL,
1054 NULL, NULL, NULL, NULL,
1055 NULL, NULL, NULL, NULL,
1056 NULL, NULL, NULL, NULL,
1058 .cpuid = {
1059 .eax = 0xd,
1060 .needs_ecx = true, .ecx = 1,
1061 .reg = R_EAX,
1063 .tcg_features = TCG_XSAVE_FEATURES,
1065 [FEAT_6_EAX] = {
1066 .type = CPUID_FEATURE_WORD,
1067 .feat_names = {
1068 NULL, NULL, "arat", NULL,
1069 NULL, NULL, NULL, NULL,
1070 NULL, NULL, NULL, NULL,
1071 NULL, NULL, NULL, NULL,
1072 NULL, NULL, NULL, NULL,
1073 NULL, NULL, NULL, NULL,
1074 NULL, NULL, NULL, NULL,
1075 NULL, NULL, NULL, NULL,
1077 .cpuid = { .eax = 6, .reg = R_EAX, },
1078 .tcg_features = TCG_6_EAX_FEATURES,
1080 [FEAT_XSAVE_COMP_LO] = {
1081 .type = CPUID_FEATURE_WORD,
1082 .cpuid = {
1083 .eax = 0xD,
1084 .needs_ecx = true, .ecx = 0,
1085 .reg = R_EAX,
1087 .tcg_features = ~0U,
1088 .migratable_flags = XSTATE_FP_MASK | XSTATE_SSE_MASK |
1089 XSTATE_YMM_MASK | XSTATE_BNDREGS_MASK | XSTATE_BNDCSR_MASK |
1090 XSTATE_OPMASK_MASK | XSTATE_ZMM_Hi256_MASK | XSTATE_Hi16_ZMM_MASK |
1091 XSTATE_PKRU_MASK,
1093 [FEAT_XSAVE_COMP_HI] = {
1094 .type = CPUID_FEATURE_WORD,
1095 .cpuid = {
1096 .eax = 0xD,
1097 .needs_ecx = true, .ecx = 0,
1098 .reg = R_EDX,
1100 .tcg_features = ~0U,
1102 /*Below are MSR exposed features*/
1103 [FEAT_ARCH_CAPABILITIES] = {
1104 .type = MSR_FEATURE_WORD,
1105 .feat_names = {
1106 "rdctl-no", "ibrs-all", "rsba", "skip-l1dfl-vmentry",
1107 "ssb-no", "mds-no", "pschange-mc-no", "tsx-ctrl",
1108 "taa-no", NULL, NULL, NULL,
1109 NULL, NULL, NULL, NULL,
1110 NULL, NULL, NULL, NULL,
1111 NULL, NULL, NULL, NULL,
1112 NULL, NULL, NULL, NULL,
1113 NULL, NULL, NULL, NULL,
1115 .msr = {
1116 .index = MSR_IA32_ARCH_CAPABILITIES,
1119 [FEAT_CORE_CAPABILITY] = {
1120 .type = MSR_FEATURE_WORD,
1121 .feat_names = {
1122 NULL, NULL, NULL, NULL,
1123 NULL, "split-lock-detect", NULL, NULL,
1124 NULL, NULL, NULL, NULL,
1125 NULL, NULL, NULL, NULL,
1126 NULL, NULL, NULL, NULL,
1127 NULL, NULL, NULL, NULL,
1128 NULL, NULL, NULL, NULL,
1129 NULL, NULL, NULL, NULL,
1131 .msr = {
1132 .index = MSR_IA32_CORE_CAPABILITY,
1135 [FEAT_PERF_CAPABILITIES] = {
1136 .type = MSR_FEATURE_WORD,
1137 .feat_names = {
1138 NULL, NULL, NULL, NULL,
1139 NULL, NULL, NULL, NULL,
1140 NULL, NULL, NULL, NULL,
1141 NULL, "full-width-write", NULL, NULL,
1142 NULL, NULL, NULL, NULL,
1143 NULL, NULL, NULL, NULL,
1144 NULL, NULL, NULL, NULL,
1145 NULL, NULL, NULL, NULL,
1147 .msr = {
1148 .index = MSR_IA32_PERF_CAPABILITIES,
1152 [FEAT_VMX_PROCBASED_CTLS] = {
1153 .type = MSR_FEATURE_WORD,
1154 .feat_names = {
1155 NULL, NULL, "vmx-vintr-pending", "vmx-tsc-offset",
1156 NULL, NULL, NULL, "vmx-hlt-exit",
1157 NULL, "vmx-invlpg-exit", "vmx-mwait-exit", "vmx-rdpmc-exit",
1158 "vmx-rdtsc-exit", NULL, NULL, "vmx-cr3-load-noexit",
1159 "vmx-cr3-store-noexit", NULL, NULL, "vmx-cr8-load-exit",
1160 "vmx-cr8-store-exit", "vmx-flexpriority", "vmx-vnmi-pending", "vmx-movdr-exit",
1161 "vmx-io-exit", "vmx-io-bitmap", NULL, "vmx-mtf",
1162 "vmx-msr-bitmap", "vmx-monitor-exit", "vmx-pause-exit", "vmx-secondary-ctls",
1164 .msr = {
1165 .index = MSR_IA32_VMX_TRUE_PROCBASED_CTLS,
1169 [FEAT_VMX_SECONDARY_CTLS] = {
1170 .type = MSR_FEATURE_WORD,
1171 .feat_names = {
1172 "vmx-apicv-xapic", "vmx-ept", "vmx-desc-exit", "vmx-rdtscp-exit",
1173 "vmx-apicv-x2apic", "vmx-vpid", "vmx-wbinvd-exit", "vmx-unrestricted-guest",
1174 "vmx-apicv-register", "vmx-apicv-vid", "vmx-ple", "vmx-rdrand-exit",
1175 "vmx-invpcid-exit", "vmx-vmfunc", "vmx-shadow-vmcs", "vmx-encls-exit",
1176 "vmx-rdseed-exit", "vmx-pml", NULL, NULL,
1177 "vmx-xsaves", NULL, NULL, NULL,
1178 NULL, NULL, NULL, NULL,
1179 NULL, NULL, NULL, NULL,
1181 .msr = {
1182 .index = MSR_IA32_VMX_PROCBASED_CTLS2,
1186 [FEAT_VMX_PINBASED_CTLS] = {
1187 .type = MSR_FEATURE_WORD,
1188 .feat_names = {
1189 "vmx-intr-exit", NULL, NULL, "vmx-nmi-exit",
1190 NULL, "vmx-vnmi", "vmx-preemption-timer", "vmx-posted-intr",
1191 NULL, NULL, NULL, NULL,
1192 NULL, NULL, NULL, NULL,
1193 NULL, NULL, NULL, NULL,
1194 NULL, NULL, NULL, NULL,
1195 NULL, NULL, NULL, NULL,
1196 NULL, NULL, NULL, NULL,
1198 .msr = {
1199 .index = MSR_IA32_VMX_TRUE_PINBASED_CTLS,
1203 [FEAT_VMX_EXIT_CTLS] = {
1204 .type = MSR_FEATURE_WORD,
1206 * VMX_VM_EXIT_HOST_ADDR_SPACE_SIZE is copied from
1207 * the LM CPUID bit.
1209 .feat_names = {
1210 NULL, NULL, "vmx-exit-nosave-debugctl", NULL,
1211 NULL, NULL, NULL, NULL,
1212 NULL, NULL /* vmx-exit-host-addr-space-size */, NULL, NULL,
1213 "vmx-exit-load-perf-global-ctrl", NULL, NULL, "vmx-exit-ack-intr",
1214 NULL, NULL, "vmx-exit-save-pat", "vmx-exit-load-pat",
1215 "vmx-exit-save-efer", "vmx-exit-load-efer",
1216 "vmx-exit-save-preemption-timer", "vmx-exit-clear-bndcfgs",
1217 NULL, "vmx-exit-clear-rtit-ctl", NULL, NULL,
1218 NULL, "vmx-exit-load-pkrs", NULL, NULL,
1220 .msr = {
1221 .index = MSR_IA32_VMX_TRUE_EXIT_CTLS,
1225 [FEAT_VMX_ENTRY_CTLS] = {
1226 .type = MSR_FEATURE_WORD,
1227 .feat_names = {
1228 NULL, NULL, "vmx-entry-noload-debugctl", NULL,
1229 NULL, NULL, NULL, NULL,
1230 NULL, "vmx-entry-ia32e-mode", NULL, NULL,
1231 NULL, "vmx-entry-load-perf-global-ctrl", "vmx-entry-load-pat", "vmx-entry-load-efer",
1232 "vmx-entry-load-bndcfgs", NULL, "vmx-entry-load-rtit-ctl", NULL,
1233 NULL, NULL, "vmx-entry-load-pkrs", NULL,
1234 NULL, NULL, NULL, NULL,
1235 NULL, NULL, NULL, NULL,
1237 .msr = {
1238 .index = MSR_IA32_VMX_TRUE_ENTRY_CTLS,
1242 [FEAT_VMX_MISC] = {
1243 .type = MSR_FEATURE_WORD,
1244 .feat_names = {
1245 NULL, NULL, NULL, NULL,
1246 NULL, "vmx-store-lma", "vmx-activity-hlt", "vmx-activity-shutdown",
1247 "vmx-activity-wait-sipi", NULL, NULL, NULL,
1248 NULL, NULL, NULL, NULL,
1249 NULL, NULL, NULL, NULL,
1250 NULL, NULL, NULL, NULL,
1251 NULL, NULL, NULL, NULL,
1252 NULL, "vmx-vmwrite-vmexit-fields", "vmx-zero-len-inject", NULL,
1254 .msr = {
1255 .index = MSR_IA32_VMX_MISC,
1259 [FEAT_VMX_EPT_VPID_CAPS] = {
1260 .type = MSR_FEATURE_WORD,
1261 .feat_names = {
1262 "vmx-ept-execonly", NULL, NULL, NULL,
1263 NULL, NULL, "vmx-page-walk-4", "vmx-page-walk-5",
1264 NULL, NULL, NULL, NULL,
1265 NULL, NULL, NULL, NULL,
1266 "vmx-ept-2mb", "vmx-ept-1gb", NULL, NULL,
1267 "vmx-invept", "vmx-eptad", "vmx-ept-advanced-exitinfo", NULL,
1268 NULL, "vmx-invept-single-context", "vmx-invept-all-context", NULL,
1269 NULL, NULL, NULL, NULL,
1270 "vmx-invvpid", NULL, NULL, NULL,
1271 NULL, NULL, NULL, NULL,
1272 "vmx-invvpid-single-addr", "vmx-invept-single-context",
1273 "vmx-invvpid-all-context", "vmx-invept-single-context-noglobals",
1274 NULL, NULL, NULL, NULL,
1275 NULL, NULL, NULL, NULL,
1276 NULL, NULL, NULL, NULL,
1277 NULL, NULL, NULL, NULL,
1278 NULL, NULL, NULL, NULL,
1280 .msr = {
1281 .index = MSR_IA32_VMX_EPT_VPID_CAP,
1285 [FEAT_VMX_BASIC] = {
1286 .type = MSR_FEATURE_WORD,
1287 .feat_names = {
1288 [54] = "vmx-ins-outs",
1289 [55] = "vmx-true-ctls",
1291 .msr = {
1292 .index = MSR_IA32_VMX_BASIC,
1294 /* Just to be safe - we don't support setting the MSEG version field. */
1295 .no_autoenable_flags = MSR_VMX_BASIC_DUAL_MONITOR,
1298 [FEAT_VMX_VMFUNC] = {
1299 .type = MSR_FEATURE_WORD,
1300 .feat_names = {
1301 [0] = "vmx-eptp-switching",
1303 .msr = {
1304 .index = MSR_IA32_VMX_VMFUNC,
1308 [FEAT_14_0_ECX] = {
1309 .type = CPUID_FEATURE_WORD,
1310 .feat_names = {
1311 NULL, NULL, NULL, NULL,
1312 NULL, NULL, NULL, NULL,
1313 NULL, NULL, NULL, NULL,
1314 NULL, NULL, NULL, NULL,
1315 NULL, NULL, NULL, NULL,
1316 NULL, NULL, NULL, NULL,
1317 NULL, NULL, NULL, NULL,
1318 NULL, NULL, NULL, "intel-pt-lip",
1320 .cpuid = {
1321 .eax = 0x14,
1322 .needs_ecx = true, .ecx = 0,
1323 .reg = R_ECX,
1325 .tcg_features = TCG_14_0_ECX_FEATURES,
1330 typedef struct FeatureMask {
1331 FeatureWord index;
1332 uint64_t mask;
1333 } FeatureMask;
1335 typedef struct FeatureDep {
1336 FeatureMask from, to;
1337 } FeatureDep;
1339 static FeatureDep feature_dependencies[] = {
1341 .from = { FEAT_7_0_EDX, CPUID_7_0_EDX_ARCH_CAPABILITIES },
1342 .to = { FEAT_ARCH_CAPABILITIES, ~0ull },
1345 .from = { FEAT_7_0_EDX, CPUID_7_0_EDX_CORE_CAPABILITY },
1346 .to = { FEAT_CORE_CAPABILITY, ~0ull },
1349 .from = { FEAT_1_ECX, CPUID_EXT_PDCM },
1350 .to = { FEAT_PERF_CAPABILITIES, ~0ull },
1353 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1354 .to = { FEAT_VMX_PROCBASED_CTLS, ~0ull },
1357 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1358 .to = { FEAT_VMX_PINBASED_CTLS, ~0ull },
1361 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1362 .to = { FEAT_VMX_EXIT_CTLS, ~0ull },
1365 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1366 .to = { FEAT_VMX_ENTRY_CTLS, ~0ull },
1369 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1370 .to = { FEAT_VMX_MISC, ~0ull },
1373 .from = { FEAT_1_ECX, CPUID_EXT_VMX },
1374 .to = { FEAT_VMX_BASIC, ~0ull },
1377 .from = { FEAT_8000_0001_EDX, CPUID_EXT2_LM },
1378 .to = { FEAT_VMX_ENTRY_CTLS, VMX_VM_ENTRY_IA32E_MODE },
1381 .from = { FEAT_VMX_PROCBASED_CTLS, VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS },
1382 .to = { FEAT_VMX_SECONDARY_CTLS, ~0ull },
1385 .from = { FEAT_XSAVE, CPUID_XSAVE_XSAVES },
1386 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_XSAVES },
1389 .from = { FEAT_1_ECX, CPUID_EXT_RDRAND },
1390 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_RDRAND_EXITING },
1393 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_INVPCID },
1394 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_INVPCID },
1397 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_RDSEED },
1398 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_RDSEED_EXITING },
1401 .from = { FEAT_7_0_EBX, CPUID_7_0_EBX_INTEL_PT },
1402 .to = { FEAT_14_0_ECX, ~0ull },
1405 .from = { FEAT_8000_0001_EDX, CPUID_EXT2_RDTSCP },
1406 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_RDTSCP },
1409 .from = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_EPT },
1410 .to = { FEAT_VMX_EPT_VPID_CAPS, 0xffffffffull },
1413 .from = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_EPT },
1414 .to = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST },
1417 .from = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_VPID },
1418 .to = { FEAT_VMX_EPT_VPID_CAPS, 0xffffffffull << 32 },
1421 .from = { FEAT_VMX_SECONDARY_CTLS, VMX_SECONDARY_EXEC_ENABLE_VMFUNC },
1422 .to = { FEAT_VMX_VMFUNC, ~0ull },
1425 .from = { FEAT_8000_0001_ECX, CPUID_EXT3_SVM },
1426 .to = { FEAT_SVM, ~0ull },
1430 typedef struct X86RegisterInfo32 {
1431 /* Name of register */
1432 const char *name;
1433 /* QAPI enum value register */
1434 X86CPURegister32 qapi_enum;
1435 } X86RegisterInfo32;
1437 #define REGISTER(reg) \
1438 [R_##reg] = { .name = #reg, .qapi_enum = X86_CPU_REGISTER32_##reg }
1439 static const X86RegisterInfo32 x86_reg_info_32[CPU_NB_REGS32] = {
1440 REGISTER(EAX),
1441 REGISTER(ECX),
1442 REGISTER(EDX),
1443 REGISTER(EBX),
1444 REGISTER(ESP),
1445 REGISTER(EBP),
1446 REGISTER(ESI),
1447 REGISTER(EDI),
1449 #undef REGISTER
1451 typedef struct ExtSaveArea {
1452 uint32_t feature, bits;
1453 uint32_t offset, size;
1454 } ExtSaveArea;
1456 static const ExtSaveArea x86_ext_save_areas[] = {
1457 [XSTATE_FP_BIT] = {
1458 /* x87 FP state component is always enabled if XSAVE is supported */
1459 .feature = FEAT_1_ECX, .bits = CPUID_EXT_XSAVE,
1460 /* x87 state is in the legacy region of the XSAVE area */
1461 .offset = 0,
1462 .size = sizeof(X86LegacyXSaveArea) + sizeof(X86XSaveHeader),
1464 [XSTATE_SSE_BIT] = {
1465 /* SSE state component is always enabled if XSAVE is supported */
1466 .feature = FEAT_1_ECX, .bits = CPUID_EXT_XSAVE,
1467 /* SSE state is in the legacy region of the XSAVE area */
1468 .offset = 0,
1469 .size = sizeof(X86LegacyXSaveArea) + sizeof(X86XSaveHeader),
1471 [XSTATE_YMM_BIT] =
1472 { .feature = FEAT_1_ECX, .bits = CPUID_EXT_AVX,
1473 .offset = offsetof(X86XSaveArea, avx_state),
1474 .size = sizeof(XSaveAVX) },
1475 [XSTATE_BNDREGS_BIT] =
1476 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_MPX,
1477 .offset = offsetof(X86XSaveArea, bndreg_state),
1478 .size = sizeof(XSaveBNDREG) },
1479 [XSTATE_BNDCSR_BIT] =
1480 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_MPX,
1481 .offset = offsetof(X86XSaveArea, bndcsr_state),
1482 .size = sizeof(XSaveBNDCSR) },
1483 [XSTATE_OPMASK_BIT] =
1484 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_AVX512F,
1485 .offset = offsetof(X86XSaveArea, opmask_state),
1486 .size = sizeof(XSaveOpmask) },
1487 [XSTATE_ZMM_Hi256_BIT] =
1488 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_AVX512F,
1489 .offset = offsetof(X86XSaveArea, zmm_hi256_state),
1490 .size = sizeof(XSaveZMM_Hi256) },
1491 [XSTATE_Hi16_ZMM_BIT] =
1492 { .feature = FEAT_7_0_EBX, .bits = CPUID_7_0_EBX_AVX512F,
1493 .offset = offsetof(X86XSaveArea, hi16_zmm_state),
1494 .size = sizeof(XSaveHi16_ZMM) },
1495 [XSTATE_PKRU_BIT] =
1496 { .feature = FEAT_7_0_ECX, .bits = CPUID_7_0_ECX_PKU,
1497 .offset = offsetof(X86XSaveArea, pkru_state),
1498 .size = sizeof(XSavePKRU) },
1501 static uint32_t xsave_area_size(uint64_t mask)
1503 int i;
1504 uint64_t ret = 0;
1506 for (i = 0; i < ARRAY_SIZE(x86_ext_save_areas); i++) {
1507 const ExtSaveArea *esa = &x86_ext_save_areas[i];
1508 if ((mask >> i) & 1) {
1509 ret = MAX(ret, esa->offset + esa->size);
1512 return ret;
1515 static inline bool accel_uses_host_cpuid(void)
1517 return kvm_enabled() || hvf_enabled();
1520 static inline uint64_t x86_cpu_xsave_components(X86CPU *cpu)
1522 return ((uint64_t)cpu->env.features[FEAT_XSAVE_COMP_HI]) << 32 |
1523 cpu->env.features[FEAT_XSAVE_COMP_LO];
1526 /* Return name of 32-bit register, from a R_* constant */
1527 static const char *get_register_name_32(unsigned int reg)
1529 if (reg >= CPU_NB_REGS32) {
1530 return NULL;
1532 return x86_reg_info_32[reg].name;
1536 * Returns the set of feature flags that are supported and migratable by
1537 * QEMU, for a given FeatureWord.
1539 static uint64_t x86_cpu_get_migratable_flags(FeatureWord w)
1541 FeatureWordInfo *wi = &feature_word_info[w];
1542 uint64_t r = 0;
1543 int i;
1545 for (i = 0; i < 64; i++) {
1546 uint64_t f = 1ULL << i;
1548 /* If the feature name is known, it is implicitly considered migratable,
1549 * unless it is explicitly set in unmigratable_flags */
1550 if ((wi->migratable_flags & f) ||
1551 (wi->feat_names[i] && !(wi->unmigratable_flags & f))) {
1552 r |= f;
1555 return r;
1558 void host_cpuid(uint32_t function, uint32_t count,
1559 uint32_t *eax, uint32_t *ebx, uint32_t *ecx, uint32_t *edx)
1561 uint32_t vec[4];
1563 #ifdef __x86_64__
1564 asm volatile("cpuid"
1565 : "=a"(vec[0]), "=b"(vec[1]),
1566 "=c"(vec[2]), "=d"(vec[3])
1567 : "0"(function), "c"(count) : "cc");
1568 #elif defined(__i386__)
1569 asm volatile("pusha \n\t"
1570 "cpuid \n\t"
1571 "mov %%eax, 0(%2) \n\t"
1572 "mov %%ebx, 4(%2) \n\t"
1573 "mov %%ecx, 8(%2) \n\t"
1574 "mov %%edx, 12(%2) \n\t"
1575 "popa"
1576 : : "a"(function), "c"(count), "S"(vec)
1577 : "memory", "cc");
1578 #else
1579 abort();
1580 #endif
1582 if (eax)
1583 *eax = vec[0];
1584 if (ebx)
1585 *ebx = vec[1];
1586 if (ecx)
1587 *ecx = vec[2];
1588 if (edx)
1589 *edx = vec[3];
1592 void host_vendor_fms(char *vendor, int *family, int *model, int *stepping)
1594 uint32_t eax, ebx, ecx, edx;
1596 host_cpuid(0x0, 0, &eax, &ebx, &ecx, &edx);
1597 x86_cpu_vendor_words2str(vendor, ebx, edx, ecx);
1599 host_cpuid(0x1, 0, &eax, &ebx, &ecx, &edx);
1600 if (family) {
1601 *family = ((eax >> 8) & 0x0F) + ((eax >> 20) & 0xFF);
1603 if (model) {
1604 *model = ((eax >> 4) & 0x0F) | ((eax & 0xF0000) >> 12);
1606 if (stepping) {
1607 *stepping = eax & 0x0F;
1611 /* CPU class name definitions: */
1613 /* Return type name for a given CPU model name
1614 * Caller is responsible for freeing the returned string.
1616 static char *x86_cpu_type_name(const char *model_name)
1618 return g_strdup_printf(X86_CPU_TYPE_NAME("%s"), model_name);
1621 static ObjectClass *x86_cpu_class_by_name(const char *cpu_model)
1623 g_autofree char *typename = x86_cpu_type_name(cpu_model);
1624 return object_class_by_name(typename);
1627 static char *x86_cpu_class_get_model_name(X86CPUClass *cc)
1629 const char *class_name = object_class_get_name(OBJECT_CLASS(cc));
1630 assert(g_str_has_suffix(class_name, X86_CPU_TYPE_SUFFIX));
1631 return g_strndup(class_name,
1632 strlen(class_name) - strlen(X86_CPU_TYPE_SUFFIX));
1635 typedef struct PropValue {
1636 const char *prop, *value;
1637 } PropValue;
1639 typedef struct X86CPUVersionDefinition {
1640 X86CPUVersion version;
1641 const char *alias;
1642 const char *note;
1643 PropValue *props;
1644 } X86CPUVersionDefinition;
1646 /* Base definition for a CPU model */
1647 typedef struct X86CPUDefinition {
1648 const char *name;
1649 uint32_t level;
1650 uint32_t xlevel;
1651 /* vendor is zero-terminated, 12 character ASCII string */
1652 char vendor[CPUID_VENDOR_SZ + 1];
1653 int family;
1654 int model;
1655 int stepping;
1656 FeatureWordArray features;
1657 const char *model_id;
1658 CPUCaches *cache_info;
1660 * Definitions for alternative versions of CPU model.
1661 * List is terminated by item with version == 0.
1662 * If NULL, version 1 will be registered automatically.
1664 const X86CPUVersionDefinition *versions;
1665 const char *deprecation_note;
1666 } X86CPUDefinition;
1668 /* Reference to a specific CPU model version */
1669 struct X86CPUModel {
1670 /* Base CPU definition */
1671 X86CPUDefinition *cpudef;
1672 /* CPU model version */
1673 X86CPUVersion version;
1674 const char *note;
1676 * If true, this is an alias CPU model.
1677 * This matters only for "-cpu help" and query-cpu-definitions
1679 bool is_alias;
1682 /* Get full model name for CPU version */
1683 static char *x86_cpu_versioned_model_name(X86CPUDefinition *cpudef,
1684 X86CPUVersion version)
1686 assert(version > 0);
1687 return g_strdup_printf("%s-v%d", cpudef->name, (int)version);
1690 static const X86CPUVersionDefinition *x86_cpu_def_get_versions(X86CPUDefinition *def)
1692 /* When X86CPUDefinition::versions is NULL, we register only v1 */
1693 static const X86CPUVersionDefinition default_version_list[] = {
1694 { 1 },
1695 { /* end of list */ }
1698 return def->versions ?: default_version_list;
1701 static CPUCaches epyc_cache_info = {
1702 .l1d_cache = &(CPUCacheInfo) {
1703 .type = DATA_CACHE,
1704 .level = 1,
1705 .size = 32 * KiB,
1706 .line_size = 64,
1707 .associativity = 8,
1708 .partitions = 1,
1709 .sets = 64,
1710 .lines_per_tag = 1,
1711 .self_init = 1,
1712 .no_invd_sharing = true,
1714 .l1i_cache = &(CPUCacheInfo) {
1715 .type = INSTRUCTION_CACHE,
1716 .level = 1,
1717 .size = 64 * KiB,
1718 .line_size = 64,
1719 .associativity = 4,
1720 .partitions = 1,
1721 .sets = 256,
1722 .lines_per_tag = 1,
1723 .self_init = 1,
1724 .no_invd_sharing = true,
1726 .l2_cache = &(CPUCacheInfo) {
1727 .type = UNIFIED_CACHE,
1728 .level = 2,
1729 .size = 512 * KiB,
1730 .line_size = 64,
1731 .associativity = 8,
1732 .partitions = 1,
1733 .sets = 1024,
1734 .lines_per_tag = 1,
1736 .l3_cache = &(CPUCacheInfo) {
1737 .type = UNIFIED_CACHE,
1738 .level = 3,
1739 .size = 8 * MiB,
1740 .line_size = 64,
1741 .associativity = 16,
1742 .partitions = 1,
1743 .sets = 8192,
1744 .lines_per_tag = 1,
1745 .self_init = true,
1746 .inclusive = true,
1747 .complex_indexing = true,
1751 static CPUCaches epyc_rome_cache_info = {
1752 .l1d_cache = &(CPUCacheInfo) {
1753 .type = DATA_CACHE,
1754 .level = 1,
1755 .size = 32 * KiB,
1756 .line_size = 64,
1757 .associativity = 8,
1758 .partitions = 1,
1759 .sets = 64,
1760 .lines_per_tag = 1,
1761 .self_init = 1,
1762 .no_invd_sharing = true,
1764 .l1i_cache = &(CPUCacheInfo) {
1765 .type = INSTRUCTION_CACHE,
1766 .level = 1,
1767 .size = 32 * KiB,
1768 .line_size = 64,
1769 .associativity = 8,
1770 .partitions = 1,
1771 .sets = 64,
1772 .lines_per_tag = 1,
1773 .self_init = 1,
1774 .no_invd_sharing = true,
1776 .l2_cache = &(CPUCacheInfo) {
1777 .type = UNIFIED_CACHE,
1778 .level = 2,
1779 .size = 512 * KiB,
1780 .line_size = 64,
1781 .associativity = 8,
1782 .partitions = 1,
1783 .sets = 1024,
1784 .lines_per_tag = 1,
1786 .l3_cache = &(CPUCacheInfo) {
1787 .type = UNIFIED_CACHE,
1788 .level = 3,
1789 .size = 16 * MiB,
1790 .line_size = 64,
1791 .associativity = 16,
1792 .partitions = 1,
1793 .sets = 16384,
1794 .lines_per_tag = 1,
1795 .self_init = true,
1796 .inclusive = true,
1797 .complex_indexing = true,
1801 static CPUCaches epyc_milan_cache_info = {
1802 .l1d_cache = &(CPUCacheInfo) {
1803 .type = DATA_CACHE,
1804 .level = 1,
1805 .size = 32 * KiB,
1806 .line_size = 64,
1807 .associativity = 8,
1808 .partitions = 1,
1809 .sets = 64,
1810 .lines_per_tag = 1,
1811 .self_init = 1,
1812 .no_invd_sharing = true,
1814 .l1i_cache = &(CPUCacheInfo) {
1815 .type = INSTRUCTION_CACHE,
1816 .level = 1,
1817 .size = 32 * KiB,
1818 .line_size = 64,
1819 .associativity = 8,
1820 .partitions = 1,
1821 .sets = 64,
1822 .lines_per_tag = 1,
1823 .self_init = 1,
1824 .no_invd_sharing = true,
1826 .l2_cache = &(CPUCacheInfo) {
1827 .type = UNIFIED_CACHE,
1828 .level = 2,
1829 .size = 512 * KiB,
1830 .line_size = 64,
1831 .associativity = 8,
1832 .partitions = 1,
1833 .sets = 1024,
1834 .lines_per_tag = 1,
1836 .l3_cache = &(CPUCacheInfo) {
1837 .type = UNIFIED_CACHE,
1838 .level = 3,
1839 .size = 32 * MiB,
1840 .line_size = 64,
1841 .associativity = 16,
1842 .partitions = 1,
1843 .sets = 32768,
1844 .lines_per_tag = 1,
1845 .self_init = true,
1846 .inclusive = true,
1847 .complex_indexing = true,
1851 /* The following VMX features are not supported by KVM and are left out in the
1852 * CPU definitions:
1854 * Dual-monitor support (all processors)
1855 * Entry to SMM
1856 * Deactivate dual-monitor treatment
1857 * Number of CR3-target values
1858 * Shutdown activity state
1859 * Wait-for-SIPI activity state
1860 * PAUSE-loop exiting (Westmere and newer)
1861 * EPT-violation #VE (Broadwell and newer)
1862 * Inject event with insn length=0 (Skylake and newer)
1863 * Conceal non-root operation from PT
1864 * Conceal VM exits from PT
1865 * Conceal VM entries from PT
1866 * Enable ENCLS exiting
1867 * Mode-based execute control (XS/XU)
1868 s TSC scaling (Skylake Server and newer)
1869 * GPA translation for PT (IceLake and newer)
1870 * User wait and pause
1871 * ENCLV exiting
1872 * Load IA32_RTIT_CTL
1873 * Clear IA32_RTIT_CTL
1874 * Advanced VM-exit information for EPT violations
1875 * Sub-page write permissions
1876 * PT in VMX operation
1879 static X86CPUDefinition builtin_x86_defs[] = {
1881 .name = "qemu64",
1882 .level = 0xd,
1883 .vendor = CPUID_VENDOR_AMD,
1884 .family = 6,
1885 .model = 6,
1886 .stepping = 3,
1887 .features[FEAT_1_EDX] =
1888 PPRO_FEATURES |
1889 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
1890 CPUID_PSE36,
1891 .features[FEAT_1_ECX] =
1892 CPUID_EXT_SSE3 | CPUID_EXT_CX16,
1893 .features[FEAT_8000_0001_EDX] =
1894 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
1895 .features[FEAT_8000_0001_ECX] =
1896 CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM,
1897 .xlevel = 0x8000000A,
1898 .model_id = "QEMU Virtual CPU version " QEMU_HW_VERSION,
1901 .name = "phenom",
1902 .level = 5,
1903 .vendor = CPUID_VENDOR_AMD,
1904 .family = 16,
1905 .model = 2,
1906 .stepping = 3,
1907 /* Missing: CPUID_HT */
1908 .features[FEAT_1_EDX] =
1909 PPRO_FEATURES |
1910 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
1911 CPUID_PSE36 | CPUID_VME,
1912 .features[FEAT_1_ECX] =
1913 CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_CX16 |
1914 CPUID_EXT_POPCNT,
1915 .features[FEAT_8000_0001_EDX] =
1916 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX |
1917 CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT | CPUID_EXT2_MMXEXT |
1918 CPUID_EXT2_FFXSR | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP,
1919 /* Missing: CPUID_EXT3_CMP_LEG, CPUID_EXT3_EXTAPIC,
1920 CPUID_EXT3_CR8LEG,
1921 CPUID_EXT3_MISALIGNSSE, CPUID_EXT3_3DNOWPREFETCH,
1922 CPUID_EXT3_OSVW, CPUID_EXT3_IBS */
1923 .features[FEAT_8000_0001_ECX] =
1924 CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM |
1925 CPUID_EXT3_ABM | CPUID_EXT3_SSE4A,
1926 /* Missing: CPUID_SVM_LBRV */
1927 .features[FEAT_SVM] =
1928 CPUID_SVM_NPT,
1929 .xlevel = 0x8000001A,
1930 .model_id = "AMD Phenom(tm) 9550 Quad-Core Processor"
1933 .name = "core2duo",
1934 .level = 10,
1935 .vendor = CPUID_VENDOR_INTEL,
1936 .family = 6,
1937 .model = 15,
1938 .stepping = 11,
1939 /* Missing: CPUID_DTS, CPUID_HT, CPUID_TM, CPUID_PBE */
1940 .features[FEAT_1_EDX] =
1941 PPRO_FEATURES |
1942 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
1943 CPUID_PSE36 | CPUID_VME | CPUID_ACPI | CPUID_SS,
1944 /* Missing: CPUID_EXT_DTES64, CPUID_EXT_DSCPL, CPUID_EXT_EST,
1945 * CPUID_EXT_TM2, CPUID_EXT_XTPR, CPUID_EXT_PDCM, CPUID_EXT_VMX */
1946 .features[FEAT_1_ECX] =
1947 CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_SSSE3 |
1948 CPUID_EXT_CX16,
1949 .features[FEAT_8000_0001_EDX] =
1950 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
1951 .features[FEAT_8000_0001_ECX] =
1952 CPUID_EXT3_LAHF_LM,
1953 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS,
1954 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
1955 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
1956 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
1957 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
1958 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS,
1959 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
1960 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
1961 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
1962 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
1963 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
1964 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
1965 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
1966 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
1967 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
1968 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
1969 .features[FEAT_VMX_SECONDARY_CTLS] =
1970 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES,
1971 .xlevel = 0x80000008,
1972 .model_id = "Intel(R) Core(TM)2 Duo CPU T7700 @ 2.40GHz",
1975 .name = "kvm64",
1976 .level = 0xd,
1977 .vendor = CPUID_VENDOR_INTEL,
1978 .family = 15,
1979 .model = 6,
1980 .stepping = 1,
1981 /* Missing: CPUID_HT */
1982 .features[FEAT_1_EDX] =
1983 PPRO_FEATURES | CPUID_VME |
1984 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
1985 CPUID_PSE36,
1986 /* Missing: CPUID_EXT_POPCNT, CPUID_EXT_MONITOR */
1987 .features[FEAT_1_ECX] =
1988 CPUID_EXT_SSE3 | CPUID_EXT_CX16,
1989 /* Missing: CPUID_EXT2_PDPE1GB, CPUID_EXT2_RDTSCP */
1990 .features[FEAT_8000_0001_EDX] =
1991 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
1992 /* Missing: CPUID_EXT3_LAHF_LM, CPUID_EXT3_CMP_LEG, CPUID_EXT3_EXTAPIC,
1993 CPUID_EXT3_CR8LEG, CPUID_EXT3_ABM, CPUID_EXT3_SSE4A,
1994 CPUID_EXT3_MISALIGNSSE, CPUID_EXT3_3DNOWPREFETCH,
1995 CPUID_EXT3_OSVW, CPUID_EXT3_IBS, CPUID_EXT3_SVM */
1996 .features[FEAT_8000_0001_ECX] =
1998 /* VMX features from Cedar Mill/Prescott */
1999 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
2000 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
2001 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
2002 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2003 VMX_PIN_BASED_NMI_EXITING,
2004 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2005 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2006 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2007 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2008 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2009 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2010 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2011 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING,
2012 .xlevel = 0x80000008,
2013 .model_id = "Common KVM processor"
2016 .name = "qemu32",
2017 .level = 4,
2018 .vendor = CPUID_VENDOR_INTEL,
2019 .family = 6,
2020 .model = 6,
2021 .stepping = 3,
2022 .features[FEAT_1_EDX] =
2023 PPRO_FEATURES,
2024 .features[FEAT_1_ECX] =
2025 CPUID_EXT_SSE3,
2026 .xlevel = 0x80000004,
2027 .model_id = "QEMU Virtual CPU version " QEMU_HW_VERSION,
2030 .name = "kvm32",
2031 .level = 5,
2032 .vendor = CPUID_VENDOR_INTEL,
2033 .family = 15,
2034 .model = 6,
2035 .stepping = 1,
2036 .features[FEAT_1_EDX] =
2037 PPRO_FEATURES | CPUID_VME |
2038 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_PSE36,
2039 .features[FEAT_1_ECX] =
2040 CPUID_EXT_SSE3,
2041 .features[FEAT_8000_0001_ECX] =
2043 /* VMX features from Yonah */
2044 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
2045 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
2046 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
2047 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2048 VMX_PIN_BASED_NMI_EXITING,
2049 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2050 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2051 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2052 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2053 VMX_CPU_BASED_MOV_DR_EXITING | VMX_CPU_BASED_UNCOND_IO_EXITING |
2054 VMX_CPU_BASED_USE_IO_BITMAPS | VMX_CPU_BASED_MONITOR_EXITING |
2055 VMX_CPU_BASED_PAUSE_EXITING | VMX_CPU_BASED_USE_MSR_BITMAPS,
2056 .xlevel = 0x80000008,
2057 .model_id = "Common 32-bit KVM processor"
2060 .name = "coreduo",
2061 .level = 10,
2062 .vendor = CPUID_VENDOR_INTEL,
2063 .family = 6,
2064 .model = 14,
2065 .stepping = 8,
2066 /* Missing: CPUID_DTS, CPUID_HT, CPUID_TM, CPUID_PBE */
2067 .features[FEAT_1_EDX] =
2068 PPRO_FEATURES | CPUID_VME |
2069 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_ACPI |
2070 CPUID_SS,
2071 /* Missing: CPUID_EXT_EST, CPUID_EXT_TM2 , CPUID_EXT_XTPR,
2072 * CPUID_EXT_PDCM, CPUID_EXT_VMX */
2073 .features[FEAT_1_ECX] =
2074 CPUID_EXT_SSE3 | CPUID_EXT_MONITOR,
2075 .features[FEAT_8000_0001_EDX] =
2076 CPUID_EXT2_NX,
2077 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
2078 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
2079 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
2080 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2081 VMX_PIN_BASED_NMI_EXITING,
2082 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2083 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2084 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2085 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2086 VMX_CPU_BASED_MOV_DR_EXITING | VMX_CPU_BASED_UNCOND_IO_EXITING |
2087 VMX_CPU_BASED_USE_IO_BITMAPS | VMX_CPU_BASED_MONITOR_EXITING |
2088 VMX_CPU_BASED_PAUSE_EXITING | VMX_CPU_BASED_USE_MSR_BITMAPS,
2089 .xlevel = 0x80000008,
2090 .model_id = "Genuine Intel(R) CPU T2600 @ 2.16GHz",
2093 .name = "486",
2094 .level = 1,
2095 .vendor = CPUID_VENDOR_INTEL,
2096 .family = 4,
2097 .model = 8,
2098 .stepping = 0,
2099 .features[FEAT_1_EDX] =
2100 I486_FEATURES,
2101 .xlevel = 0,
2102 .model_id = "",
2105 .name = "pentium",
2106 .level = 1,
2107 .vendor = CPUID_VENDOR_INTEL,
2108 .family = 5,
2109 .model = 4,
2110 .stepping = 3,
2111 .features[FEAT_1_EDX] =
2112 PENTIUM_FEATURES,
2113 .xlevel = 0,
2114 .model_id = "",
2117 .name = "pentium2",
2118 .level = 2,
2119 .vendor = CPUID_VENDOR_INTEL,
2120 .family = 6,
2121 .model = 5,
2122 .stepping = 2,
2123 .features[FEAT_1_EDX] =
2124 PENTIUM2_FEATURES,
2125 .xlevel = 0,
2126 .model_id = "",
2129 .name = "pentium3",
2130 .level = 3,
2131 .vendor = CPUID_VENDOR_INTEL,
2132 .family = 6,
2133 .model = 7,
2134 .stepping = 3,
2135 .features[FEAT_1_EDX] =
2136 PENTIUM3_FEATURES,
2137 .xlevel = 0,
2138 .model_id = "",
2141 .name = "athlon",
2142 .level = 2,
2143 .vendor = CPUID_VENDOR_AMD,
2144 .family = 6,
2145 .model = 2,
2146 .stepping = 3,
2147 .features[FEAT_1_EDX] =
2148 PPRO_FEATURES | CPUID_PSE36 | CPUID_VME | CPUID_MTRR |
2149 CPUID_MCA,
2150 .features[FEAT_8000_0001_EDX] =
2151 CPUID_EXT2_MMXEXT | CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT,
2152 .xlevel = 0x80000008,
2153 .model_id = "QEMU Virtual CPU version " QEMU_HW_VERSION,
2156 .name = "n270",
2157 .level = 10,
2158 .vendor = CPUID_VENDOR_INTEL,
2159 .family = 6,
2160 .model = 28,
2161 .stepping = 2,
2162 /* Missing: CPUID_DTS, CPUID_HT, CPUID_TM, CPUID_PBE */
2163 .features[FEAT_1_EDX] =
2164 PPRO_FEATURES |
2165 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_VME |
2166 CPUID_ACPI | CPUID_SS,
2167 /* Some CPUs got no CPUID_SEP */
2168 /* Missing: CPUID_EXT_DSCPL, CPUID_EXT_EST, CPUID_EXT_TM2,
2169 * CPUID_EXT_XTPR */
2170 .features[FEAT_1_ECX] =
2171 CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_SSSE3 |
2172 CPUID_EXT_MOVBE,
2173 .features[FEAT_8000_0001_EDX] =
2174 CPUID_EXT2_NX,
2175 .features[FEAT_8000_0001_ECX] =
2176 CPUID_EXT3_LAHF_LM,
2177 .xlevel = 0x80000008,
2178 .model_id = "Intel(R) Atom(TM) CPU N270 @ 1.60GHz",
2181 .name = "Conroe",
2182 .level = 10,
2183 .vendor = CPUID_VENDOR_INTEL,
2184 .family = 6,
2185 .model = 15,
2186 .stepping = 3,
2187 .features[FEAT_1_EDX] =
2188 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2189 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2190 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2191 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2192 CPUID_DE | CPUID_FP87,
2193 .features[FEAT_1_ECX] =
2194 CPUID_EXT_SSSE3 | CPUID_EXT_SSE3,
2195 .features[FEAT_8000_0001_EDX] =
2196 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
2197 .features[FEAT_8000_0001_ECX] =
2198 CPUID_EXT3_LAHF_LM,
2199 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS,
2200 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE,
2201 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT,
2202 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
2203 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2204 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS,
2205 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2206 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2207 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2208 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2209 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2210 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2211 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2212 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2213 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2214 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2215 .features[FEAT_VMX_SECONDARY_CTLS] =
2216 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES,
2217 .xlevel = 0x80000008,
2218 .model_id = "Intel Celeron_4x0 (Conroe/Merom Class Core 2)",
2221 .name = "Penryn",
2222 .level = 10,
2223 .vendor = CPUID_VENDOR_INTEL,
2224 .family = 6,
2225 .model = 23,
2226 .stepping = 3,
2227 .features[FEAT_1_EDX] =
2228 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2229 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2230 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2231 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2232 CPUID_DE | CPUID_FP87,
2233 .features[FEAT_1_ECX] =
2234 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2235 CPUID_EXT_SSE3,
2236 .features[FEAT_8000_0001_EDX] =
2237 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
2238 .features[FEAT_8000_0001_ECX] =
2239 CPUID_EXT3_LAHF_LM,
2240 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS,
2241 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2242 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL,
2243 .features[FEAT_VMX_EXIT_CTLS] = VMX_VM_EXIT_ACK_INTR_ON_EXIT |
2244 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL,
2245 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
2246 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2247 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS,
2248 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2249 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2250 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2251 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2252 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2253 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2254 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2255 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2256 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2257 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2258 .features[FEAT_VMX_SECONDARY_CTLS] =
2259 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2260 VMX_SECONDARY_EXEC_WBINVD_EXITING,
2261 .xlevel = 0x80000008,
2262 .model_id = "Intel Core 2 Duo P9xxx (Penryn Class Core 2)",
2265 .name = "Nehalem",
2266 .level = 11,
2267 .vendor = CPUID_VENDOR_INTEL,
2268 .family = 6,
2269 .model = 26,
2270 .stepping = 3,
2271 .features[FEAT_1_EDX] =
2272 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2273 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2274 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2275 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2276 CPUID_DE | CPUID_FP87,
2277 .features[FEAT_1_ECX] =
2278 CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
2279 CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_SSE3,
2280 .features[FEAT_8000_0001_EDX] =
2281 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
2282 .features[FEAT_8000_0001_ECX] =
2283 CPUID_EXT3_LAHF_LM,
2284 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2285 MSR_VMX_BASIC_TRUE_CTLS,
2286 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2287 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2288 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2289 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2290 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2291 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2292 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2293 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2294 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2295 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
2296 .features[FEAT_VMX_EXIT_CTLS] =
2297 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2298 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2299 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2300 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2301 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2302 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT,
2303 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2304 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2305 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
2306 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2307 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2308 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2309 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2310 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2311 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2312 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2313 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2314 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2315 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2316 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2317 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2318 .features[FEAT_VMX_SECONDARY_CTLS] =
2319 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2320 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2321 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2322 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2323 VMX_SECONDARY_EXEC_ENABLE_VPID,
2324 .xlevel = 0x80000008,
2325 .model_id = "Intel Core i7 9xx (Nehalem Class Core i7)",
2326 .versions = (X86CPUVersionDefinition[]) {
2327 { .version = 1 },
2329 .version = 2,
2330 .alias = "Nehalem-IBRS",
2331 .props = (PropValue[]) {
2332 { "spec-ctrl", "on" },
2333 { "model-id",
2334 "Intel Core i7 9xx (Nehalem Core i7, IBRS update)" },
2335 { /* end of list */ }
2338 { /* end of list */ }
2342 .name = "Westmere",
2343 .level = 11,
2344 .vendor = CPUID_VENDOR_INTEL,
2345 .family = 6,
2346 .model = 44,
2347 .stepping = 1,
2348 .features[FEAT_1_EDX] =
2349 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2350 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2351 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2352 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2353 CPUID_DE | CPUID_FP87,
2354 .features[FEAT_1_ECX] =
2355 CPUID_EXT_AES | CPUID_EXT_POPCNT | CPUID_EXT_SSE42 |
2356 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2357 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3,
2358 .features[FEAT_8000_0001_EDX] =
2359 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
2360 .features[FEAT_8000_0001_ECX] =
2361 CPUID_EXT3_LAHF_LM,
2362 .features[FEAT_6_EAX] =
2363 CPUID_6_EAX_ARAT,
2364 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2365 MSR_VMX_BASIC_TRUE_CTLS,
2366 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2367 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2368 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2369 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2370 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2371 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2372 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2373 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2374 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2375 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
2376 .features[FEAT_VMX_EXIT_CTLS] =
2377 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2378 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2379 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2380 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2381 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2382 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2383 MSR_VMX_MISC_STORE_LMA,
2384 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2385 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2386 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
2387 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2388 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2389 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2390 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2391 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2392 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2393 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2394 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2395 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2396 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2397 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2398 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2399 .features[FEAT_VMX_SECONDARY_CTLS] =
2400 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2401 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2402 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2403 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2404 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST,
2405 .xlevel = 0x80000008,
2406 .model_id = "Westmere E56xx/L56xx/X56xx (Nehalem-C)",
2407 .versions = (X86CPUVersionDefinition[]) {
2408 { .version = 1 },
2410 .version = 2,
2411 .alias = "Westmere-IBRS",
2412 .props = (PropValue[]) {
2413 { "spec-ctrl", "on" },
2414 { "model-id",
2415 "Westmere E56xx/L56xx/X56xx (IBRS update)" },
2416 { /* end of list */ }
2419 { /* end of list */ }
2423 .name = "SandyBridge",
2424 .level = 0xd,
2425 .vendor = CPUID_VENDOR_INTEL,
2426 .family = 6,
2427 .model = 42,
2428 .stepping = 1,
2429 .features[FEAT_1_EDX] =
2430 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2431 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2432 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2433 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2434 CPUID_DE | CPUID_FP87,
2435 .features[FEAT_1_ECX] =
2436 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2437 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_POPCNT |
2438 CPUID_EXT_X2APIC | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
2439 CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ |
2440 CPUID_EXT_SSE3,
2441 .features[FEAT_8000_0001_EDX] =
2442 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
2443 CPUID_EXT2_SYSCALL,
2444 .features[FEAT_8000_0001_ECX] =
2445 CPUID_EXT3_LAHF_LM,
2446 .features[FEAT_XSAVE] =
2447 CPUID_XSAVE_XSAVEOPT,
2448 .features[FEAT_6_EAX] =
2449 CPUID_6_EAX_ARAT,
2450 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2451 MSR_VMX_BASIC_TRUE_CTLS,
2452 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2453 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2454 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2455 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2456 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2457 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2458 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2459 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2460 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2461 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
2462 .features[FEAT_VMX_EXIT_CTLS] =
2463 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2464 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2465 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2466 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2467 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2468 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2469 MSR_VMX_MISC_STORE_LMA,
2470 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2471 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2472 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
2473 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2474 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2475 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2476 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2477 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2478 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2479 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2480 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2481 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2482 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2483 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2484 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2485 .features[FEAT_VMX_SECONDARY_CTLS] =
2486 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2487 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2488 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2489 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2490 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST,
2491 .xlevel = 0x80000008,
2492 .model_id = "Intel Xeon E312xx (Sandy Bridge)",
2493 .versions = (X86CPUVersionDefinition[]) {
2494 { .version = 1 },
2496 .version = 2,
2497 .alias = "SandyBridge-IBRS",
2498 .props = (PropValue[]) {
2499 { "spec-ctrl", "on" },
2500 { "model-id",
2501 "Intel Xeon E312xx (Sandy Bridge, IBRS update)" },
2502 { /* end of list */ }
2505 { /* end of list */ }
2509 .name = "IvyBridge",
2510 .level = 0xd,
2511 .vendor = CPUID_VENDOR_INTEL,
2512 .family = 6,
2513 .model = 58,
2514 .stepping = 9,
2515 .features[FEAT_1_EDX] =
2516 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2517 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2518 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2519 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2520 CPUID_DE | CPUID_FP87,
2521 .features[FEAT_1_ECX] =
2522 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2523 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_POPCNT |
2524 CPUID_EXT_X2APIC | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
2525 CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ |
2526 CPUID_EXT_SSE3 | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
2527 .features[FEAT_7_0_EBX] =
2528 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_SMEP |
2529 CPUID_7_0_EBX_ERMS,
2530 .features[FEAT_8000_0001_EDX] =
2531 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
2532 CPUID_EXT2_SYSCALL,
2533 .features[FEAT_8000_0001_ECX] =
2534 CPUID_EXT3_LAHF_LM,
2535 .features[FEAT_XSAVE] =
2536 CPUID_XSAVE_XSAVEOPT,
2537 .features[FEAT_6_EAX] =
2538 CPUID_6_EAX_ARAT,
2539 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2540 MSR_VMX_BASIC_TRUE_CTLS,
2541 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2542 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2543 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2544 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2545 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2546 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2547 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2548 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2549 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2550 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS,
2551 .features[FEAT_VMX_EXIT_CTLS] =
2552 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2553 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2554 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2555 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2556 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2557 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2558 MSR_VMX_MISC_STORE_LMA,
2559 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2560 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2561 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
2562 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2563 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2564 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2565 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2566 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2567 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2568 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2569 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2570 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2571 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2572 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2573 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2574 .features[FEAT_VMX_SECONDARY_CTLS] =
2575 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2576 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2577 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2578 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2579 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
2580 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
2581 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
2582 VMX_SECONDARY_EXEC_RDRAND_EXITING,
2583 .xlevel = 0x80000008,
2584 .model_id = "Intel Xeon E3-12xx v2 (Ivy Bridge)",
2585 .versions = (X86CPUVersionDefinition[]) {
2586 { .version = 1 },
2588 .version = 2,
2589 .alias = "IvyBridge-IBRS",
2590 .props = (PropValue[]) {
2591 { "spec-ctrl", "on" },
2592 { "model-id",
2593 "Intel Xeon E3-12xx v2 (Ivy Bridge, IBRS)" },
2594 { /* end of list */ }
2597 { /* end of list */ }
2601 .name = "Haswell",
2602 .level = 0xd,
2603 .vendor = CPUID_VENDOR_INTEL,
2604 .family = 6,
2605 .model = 60,
2606 .stepping = 4,
2607 .features[FEAT_1_EDX] =
2608 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2609 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2610 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2611 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2612 CPUID_DE | CPUID_FP87,
2613 .features[FEAT_1_ECX] =
2614 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2615 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
2616 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2617 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
2618 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
2619 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
2620 .features[FEAT_8000_0001_EDX] =
2621 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
2622 CPUID_EXT2_SYSCALL,
2623 .features[FEAT_8000_0001_ECX] =
2624 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM,
2625 .features[FEAT_7_0_EBX] =
2626 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
2627 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
2628 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
2629 CPUID_7_0_EBX_RTM,
2630 .features[FEAT_XSAVE] =
2631 CPUID_XSAVE_XSAVEOPT,
2632 .features[FEAT_6_EAX] =
2633 CPUID_6_EAX_ARAT,
2634 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2635 MSR_VMX_BASIC_TRUE_CTLS,
2636 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2637 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2638 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2639 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2640 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2641 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2642 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2643 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2644 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2645 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
2646 .features[FEAT_VMX_EXIT_CTLS] =
2647 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2648 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2649 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2650 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2651 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2652 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2653 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
2654 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2655 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2656 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
2657 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2658 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2659 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2660 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2661 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2662 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2663 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2664 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2665 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2666 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2667 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2668 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2669 .features[FEAT_VMX_SECONDARY_CTLS] =
2670 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2671 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2672 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2673 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2674 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
2675 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
2676 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
2677 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
2678 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS,
2679 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
2680 .xlevel = 0x80000008,
2681 .model_id = "Intel Core Processor (Haswell)",
2682 .versions = (X86CPUVersionDefinition[]) {
2683 { .version = 1 },
2685 .version = 2,
2686 .alias = "Haswell-noTSX",
2687 .props = (PropValue[]) {
2688 { "hle", "off" },
2689 { "rtm", "off" },
2690 { "stepping", "1" },
2691 { "model-id", "Intel Core Processor (Haswell, no TSX)", },
2692 { /* end of list */ }
2696 .version = 3,
2697 .alias = "Haswell-IBRS",
2698 .props = (PropValue[]) {
2699 /* Restore TSX features removed by -v2 above */
2700 { "hle", "on" },
2701 { "rtm", "on" },
2703 * Haswell and Haswell-IBRS had stepping=4 in
2704 * QEMU 4.0 and older
2706 { "stepping", "4" },
2707 { "spec-ctrl", "on" },
2708 { "model-id",
2709 "Intel Core Processor (Haswell, IBRS)" },
2710 { /* end of list */ }
2714 .version = 4,
2715 .alias = "Haswell-noTSX-IBRS",
2716 .props = (PropValue[]) {
2717 { "hle", "off" },
2718 { "rtm", "off" },
2719 /* spec-ctrl was already enabled by -v3 above */
2720 { "stepping", "1" },
2721 { "model-id",
2722 "Intel Core Processor (Haswell, no TSX, IBRS)" },
2723 { /* end of list */ }
2726 { /* end of list */ }
2730 .name = "Broadwell",
2731 .level = 0xd,
2732 .vendor = CPUID_VENDOR_INTEL,
2733 .family = 6,
2734 .model = 61,
2735 .stepping = 2,
2736 .features[FEAT_1_EDX] =
2737 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2738 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2739 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2740 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2741 CPUID_DE | CPUID_FP87,
2742 .features[FEAT_1_ECX] =
2743 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2744 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
2745 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2746 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
2747 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
2748 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
2749 .features[FEAT_8000_0001_EDX] =
2750 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
2751 CPUID_EXT2_SYSCALL,
2752 .features[FEAT_8000_0001_ECX] =
2753 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
2754 .features[FEAT_7_0_EBX] =
2755 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
2756 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
2757 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
2758 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
2759 CPUID_7_0_EBX_SMAP,
2760 .features[FEAT_XSAVE] =
2761 CPUID_XSAVE_XSAVEOPT,
2762 .features[FEAT_6_EAX] =
2763 CPUID_6_EAX_ARAT,
2764 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2765 MSR_VMX_BASIC_TRUE_CTLS,
2766 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2767 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2768 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2769 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2770 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2771 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2772 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2773 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2774 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2775 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
2776 .features[FEAT_VMX_EXIT_CTLS] =
2777 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2778 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2779 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2780 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2781 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2782 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2783 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
2784 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2785 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2786 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
2787 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2788 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2789 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2790 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2791 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2792 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2793 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2794 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2795 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2796 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2797 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2798 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2799 .features[FEAT_VMX_SECONDARY_CTLS] =
2800 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2801 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2802 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2803 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
2804 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
2805 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
2806 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
2807 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
2808 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
2809 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
2810 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
2811 .xlevel = 0x80000008,
2812 .model_id = "Intel Core Processor (Broadwell)",
2813 .versions = (X86CPUVersionDefinition[]) {
2814 { .version = 1 },
2816 .version = 2,
2817 .alias = "Broadwell-noTSX",
2818 .props = (PropValue[]) {
2819 { "hle", "off" },
2820 { "rtm", "off" },
2821 { "model-id", "Intel Core Processor (Broadwell, no TSX)", },
2822 { /* end of list */ }
2826 .version = 3,
2827 .alias = "Broadwell-IBRS",
2828 .props = (PropValue[]) {
2829 /* Restore TSX features removed by -v2 above */
2830 { "hle", "on" },
2831 { "rtm", "on" },
2832 { "spec-ctrl", "on" },
2833 { "model-id",
2834 "Intel Core Processor (Broadwell, IBRS)" },
2835 { /* end of list */ }
2839 .version = 4,
2840 .alias = "Broadwell-noTSX-IBRS",
2841 .props = (PropValue[]) {
2842 { "hle", "off" },
2843 { "rtm", "off" },
2844 /* spec-ctrl was already enabled by -v3 above */
2845 { "model-id",
2846 "Intel Core Processor (Broadwell, no TSX, IBRS)" },
2847 { /* end of list */ }
2850 { /* end of list */ }
2854 .name = "Skylake-Client",
2855 .level = 0xd,
2856 .vendor = CPUID_VENDOR_INTEL,
2857 .family = 6,
2858 .model = 94,
2859 .stepping = 3,
2860 .features[FEAT_1_EDX] =
2861 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2862 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2863 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2864 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2865 CPUID_DE | CPUID_FP87,
2866 .features[FEAT_1_ECX] =
2867 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2868 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
2869 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2870 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
2871 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
2872 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
2873 .features[FEAT_8000_0001_EDX] =
2874 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
2875 CPUID_EXT2_SYSCALL,
2876 .features[FEAT_8000_0001_ECX] =
2877 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
2878 .features[FEAT_7_0_EBX] =
2879 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
2880 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
2881 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
2882 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
2883 CPUID_7_0_EBX_SMAP,
2884 /* Missing: XSAVES (not supported by some Linux versions,
2885 * including v4.1 to v4.12).
2886 * KVM doesn't yet expose any XSAVES state save component,
2887 * and the only one defined in Skylake (processor tracing)
2888 * probably will block migration anyway.
2890 .features[FEAT_XSAVE] =
2891 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
2892 CPUID_XSAVE_XGETBV1,
2893 .features[FEAT_6_EAX] =
2894 CPUID_6_EAX_ARAT,
2895 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
2896 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
2897 MSR_VMX_BASIC_TRUE_CTLS,
2898 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
2899 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
2900 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
2901 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
2902 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
2903 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
2904 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
2905 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
2906 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
2907 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
2908 .features[FEAT_VMX_EXIT_CTLS] =
2909 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
2910 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
2911 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
2912 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
2913 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
2914 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
2915 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
2916 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
2917 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
2918 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
2919 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
2920 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
2921 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
2922 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
2923 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
2924 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
2925 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
2926 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
2927 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
2928 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
2929 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
2930 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
2931 .features[FEAT_VMX_SECONDARY_CTLS] =
2932 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
2933 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
2934 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
2935 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
2936 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
2937 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
2938 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
2939 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
2940 .xlevel = 0x80000008,
2941 .model_id = "Intel Core Processor (Skylake)",
2942 .versions = (X86CPUVersionDefinition[]) {
2943 { .version = 1 },
2945 .version = 2,
2946 .alias = "Skylake-Client-IBRS",
2947 .props = (PropValue[]) {
2948 { "spec-ctrl", "on" },
2949 { "model-id",
2950 "Intel Core Processor (Skylake, IBRS)" },
2951 { /* end of list */ }
2955 .version = 3,
2956 .alias = "Skylake-Client-noTSX-IBRS",
2957 .props = (PropValue[]) {
2958 { "hle", "off" },
2959 { "rtm", "off" },
2960 { "model-id",
2961 "Intel Core Processor (Skylake, IBRS, no TSX)" },
2962 { /* end of list */ }
2965 { /* end of list */ }
2969 .name = "Skylake-Server",
2970 .level = 0xd,
2971 .vendor = CPUID_VENDOR_INTEL,
2972 .family = 6,
2973 .model = 85,
2974 .stepping = 4,
2975 .features[FEAT_1_EDX] =
2976 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
2977 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
2978 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
2979 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
2980 CPUID_DE | CPUID_FP87,
2981 .features[FEAT_1_ECX] =
2982 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
2983 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
2984 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
2985 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
2986 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
2987 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
2988 .features[FEAT_8000_0001_EDX] =
2989 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
2990 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
2991 .features[FEAT_8000_0001_ECX] =
2992 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
2993 .features[FEAT_7_0_EBX] =
2994 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
2995 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
2996 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
2997 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
2998 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLWB |
2999 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
3000 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512CD |
3001 CPUID_7_0_EBX_AVX512VL | CPUID_7_0_EBX_CLFLUSHOPT,
3002 .features[FEAT_7_0_ECX] =
3003 CPUID_7_0_ECX_PKU,
3004 /* Missing: XSAVES (not supported by some Linux versions,
3005 * including v4.1 to v4.12).
3006 * KVM doesn't yet expose any XSAVES state save component,
3007 * and the only one defined in Skylake (processor tracing)
3008 * probably will block migration anyway.
3010 .features[FEAT_XSAVE] =
3011 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3012 CPUID_XSAVE_XGETBV1,
3013 .features[FEAT_6_EAX] =
3014 CPUID_6_EAX_ARAT,
3015 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
3016 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3017 MSR_VMX_BASIC_TRUE_CTLS,
3018 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3019 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3020 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3021 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3022 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3023 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3024 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3025 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3026 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3027 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3028 .features[FEAT_VMX_EXIT_CTLS] =
3029 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3030 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3031 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3032 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3033 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3034 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3035 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3036 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3037 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3038 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3039 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3040 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3041 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3042 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3043 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3044 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3045 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3046 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3047 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3048 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3049 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3050 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3051 .features[FEAT_VMX_SECONDARY_CTLS] =
3052 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3053 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3054 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3055 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3056 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3057 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3058 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3059 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3060 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3061 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3062 .xlevel = 0x80000008,
3063 .model_id = "Intel Xeon Processor (Skylake)",
3064 .versions = (X86CPUVersionDefinition[]) {
3065 { .version = 1 },
3067 .version = 2,
3068 .alias = "Skylake-Server-IBRS",
3069 .props = (PropValue[]) {
3070 /* clflushopt was not added to Skylake-Server-IBRS */
3071 /* TODO: add -v3 including clflushopt */
3072 { "clflushopt", "off" },
3073 { "spec-ctrl", "on" },
3074 { "model-id",
3075 "Intel Xeon Processor (Skylake, IBRS)" },
3076 { /* end of list */ }
3080 .version = 3,
3081 .alias = "Skylake-Server-noTSX-IBRS",
3082 .props = (PropValue[]) {
3083 { "hle", "off" },
3084 { "rtm", "off" },
3085 { "model-id",
3086 "Intel Xeon Processor (Skylake, IBRS, no TSX)" },
3087 { /* end of list */ }
3091 .version = 4,
3092 .props = (PropValue[]) {
3093 { "vmx-eptp-switching", "on" },
3094 { /* end of list */ }
3097 { /* end of list */ }
3101 .name = "Cascadelake-Server",
3102 .level = 0xd,
3103 .vendor = CPUID_VENDOR_INTEL,
3104 .family = 6,
3105 .model = 85,
3106 .stepping = 6,
3107 .features[FEAT_1_EDX] =
3108 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3109 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3110 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3111 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3112 CPUID_DE | CPUID_FP87,
3113 .features[FEAT_1_ECX] =
3114 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3115 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3116 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3117 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3118 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3119 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3120 .features[FEAT_8000_0001_EDX] =
3121 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
3122 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3123 .features[FEAT_8000_0001_ECX] =
3124 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3125 .features[FEAT_7_0_EBX] =
3126 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
3127 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
3128 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
3129 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
3130 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLWB |
3131 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
3132 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512CD |
3133 CPUID_7_0_EBX_AVX512VL | CPUID_7_0_EBX_CLFLUSHOPT,
3134 .features[FEAT_7_0_ECX] =
3135 CPUID_7_0_ECX_PKU |
3136 CPUID_7_0_ECX_AVX512VNNI,
3137 .features[FEAT_7_0_EDX] =
3138 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_SPEC_CTRL_SSBD,
3139 /* Missing: XSAVES (not supported by some Linux versions,
3140 * including v4.1 to v4.12).
3141 * KVM doesn't yet expose any XSAVES state save component,
3142 * and the only one defined in Skylake (processor tracing)
3143 * probably will block migration anyway.
3145 .features[FEAT_XSAVE] =
3146 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3147 CPUID_XSAVE_XGETBV1,
3148 .features[FEAT_6_EAX] =
3149 CPUID_6_EAX_ARAT,
3150 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
3151 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3152 MSR_VMX_BASIC_TRUE_CTLS,
3153 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3154 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3155 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3156 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3157 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3158 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3159 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3160 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3161 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3162 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3163 .features[FEAT_VMX_EXIT_CTLS] =
3164 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3165 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3166 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3167 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3168 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3169 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3170 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3171 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3172 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3173 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3174 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3175 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3176 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3177 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3178 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3179 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3180 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3181 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3182 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3183 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3184 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3185 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3186 .features[FEAT_VMX_SECONDARY_CTLS] =
3187 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3188 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3189 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3190 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3191 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3192 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3193 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3194 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3195 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3196 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3197 .xlevel = 0x80000008,
3198 .model_id = "Intel Xeon Processor (Cascadelake)",
3199 .versions = (X86CPUVersionDefinition[]) {
3200 { .version = 1 },
3201 { .version = 2,
3202 .note = "ARCH_CAPABILITIES",
3203 .props = (PropValue[]) {
3204 { "arch-capabilities", "on" },
3205 { "rdctl-no", "on" },
3206 { "ibrs-all", "on" },
3207 { "skip-l1dfl-vmentry", "on" },
3208 { "mds-no", "on" },
3209 { /* end of list */ }
3212 { .version = 3,
3213 .alias = "Cascadelake-Server-noTSX",
3214 .note = "ARCH_CAPABILITIES, no TSX",
3215 .props = (PropValue[]) {
3216 { "hle", "off" },
3217 { "rtm", "off" },
3218 { /* end of list */ }
3221 { .version = 4,
3222 .note = "ARCH_CAPABILITIES, no TSX",
3223 .props = (PropValue[]) {
3224 { "vmx-eptp-switching", "on" },
3225 { /* end of list */ }
3228 { /* end of list */ }
3232 .name = "Cooperlake",
3233 .level = 0xd,
3234 .vendor = CPUID_VENDOR_INTEL,
3235 .family = 6,
3236 .model = 85,
3237 .stepping = 10,
3238 .features[FEAT_1_EDX] =
3239 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3240 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3241 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3242 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3243 CPUID_DE | CPUID_FP87,
3244 .features[FEAT_1_ECX] =
3245 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3246 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3247 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3248 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3249 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3250 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3251 .features[FEAT_8000_0001_EDX] =
3252 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
3253 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3254 .features[FEAT_8000_0001_ECX] =
3255 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3256 .features[FEAT_7_0_EBX] =
3257 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
3258 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
3259 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
3260 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
3261 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLWB |
3262 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
3263 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512CD |
3264 CPUID_7_0_EBX_AVX512VL | CPUID_7_0_EBX_CLFLUSHOPT,
3265 .features[FEAT_7_0_ECX] =
3266 CPUID_7_0_ECX_PKU |
3267 CPUID_7_0_ECX_AVX512VNNI,
3268 .features[FEAT_7_0_EDX] =
3269 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_STIBP |
3270 CPUID_7_0_EDX_SPEC_CTRL_SSBD | CPUID_7_0_EDX_ARCH_CAPABILITIES,
3271 .features[FEAT_ARCH_CAPABILITIES] =
3272 MSR_ARCH_CAP_RDCL_NO | MSR_ARCH_CAP_IBRS_ALL |
3273 MSR_ARCH_CAP_SKIP_L1DFL_VMENTRY | MSR_ARCH_CAP_MDS_NO |
3274 MSR_ARCH_CAP_PSCHANGE_MC_NO | MSR_ARCH_CAP_TAA_NO,
3275 .features[FEAT_7_1_EAX] =
3276 CPUID_7_1_EAX_AVX512_BF16,
3278 * Missing: XSAVES (not supported by some Linux versions,
3279 * including v4.1 to v4.12).
3280 * KVM doesn't yet expose any XSAVES state save component,
3281 * and the only one defined in Skylake (processor tracing)
3282 * probably will block migration anyway.
3284 .features[FEAT_XSAVE] =
3285 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3286 CPUID_XSAVE_XGETBV1,
3287 .features[FEAT_6_EAX] =
3288 CPUID_6_EAX_ARAT,
3289 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
3290 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3291 MSR_VMX_BASIC_TRUE_CTLS,
3292 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3293 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3294 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3295 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3296 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3297 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3298 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3299 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3300 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3301 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3302 .features[FEAT_VMX_EXIT_CTLS] =
3303 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3304 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3305 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3306 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3307 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3308 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3309 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3310 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3311 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3312 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3313 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3314 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3315 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3316 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3317 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3318 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3319 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3320 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3321 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3322 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3323 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3324 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3325 .features[FEAT_VMX_SECONDARY_CTLS] =
3326 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3327 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3328 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3329 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3330 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3331 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3332 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3333 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3334 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3335 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3336 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
3337 .xlevel = 0x80000008,
3338 .model_id = "Intel Xeon Processor (Cooperlake)",
3341 .name = "Icelake-Client",
3342 .level = 0xd,
3343 .vendor = CPUID_VENDOR_INTEL,
3344 .family = 6,
3345 .model = 126,
3346 .stepping = 0,
3347 .features[FEAT_1_EDX] =
3348 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3349 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3350 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3351 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3352 CPUID_DE | CPUID_FP87,
3353 .features[FEAT_1_ECX] =
3354 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3355 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3356 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3357 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3358 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3359 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3360 .features[FEAT_8000_0001_EDX] =
3361 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX |
3362 CPUID_EXT2_SYSCALL,
3363 .features[FEAT_8000_0001_ECX] =
3364 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3365 .features[FEAT_8000_0008_EBX] =
3366 CPUID_8000_0008_EBX_WBNOINVD,
3367 .features[FEAT_7_0_EBX] =
3368 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
3369 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
3370 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
3371 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
3372 CPUID_7_0_EBX_SMAP,
3373 .features[FEAT_7_0_ECX] =
3374 CPUID_7_0_ECX_AVX512_VBMI | CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_PKU |
3375 CPUID_7_0_ECX_AVX512_VBMI2 | CPUID_7_0_ECX_GFNI |
3376 CPUID_7_0_ECX_VAES | CPUID_7_0_ECX_VPCLMULQDQ |
3377 CPUID_7_0_ECX_AVX512VNNI | CPUID_7_0_ECX_AVX512BITALG |
3378 CPUID_7_0_ECX_AVX512_VPOPCNTDQ,
3379 .features[FEAT_7_0_EDX] =
3380 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_SPEC_CTRL_SSBD,
3381 /* Missing: XSAVES (not supported by some Linux versions,
3382 * including v4.1 to v4.12).
3383 * KVM doesn't yet expose any XSAVES state save component,
3384 * and the only one defined in Skylake (processor tracing)
3385 * probably will block migration anyway.
3387 .features[FEAT_XSAVE] =
3388 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3389 CPUID_XSAVE_XGETBV1,
3390 .features[FEAT_6_EAX] =
3391 CPUID_6_EAX_ARAT,
3392 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
3393 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3394 MSR_VMX_BASIC_TRUE_CTLS,
3395 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3396 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3397 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3398 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3399 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3400 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3401 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3402 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3403 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3404 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3405 .features[FEAT_VMX_EXIT_CTLS] =
3406 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3407 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3408 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3409 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3410 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3411 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3412 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3413 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3414 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3415 VMX_PIN_BASED_VMX_PREEMPTION_TIMER,
3416 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3417 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3418 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3419 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3420 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3421 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3422 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3423 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3424 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3425 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3426 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3427 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3428 .features[FEAT_VMX_SECONDARY_CTLS] =
3429 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3430 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3431 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3432 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3433 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3434 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3435 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3436 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
3437 .xlevel = 0x80000008,
3438 .model_id = "Intel Core Processor (Icelake)",
3439 .versions = (X86CPUVersionDefinition[]) {
3441 .version = 1,
3442 .note = "deprecated"
3445 .version = 2,
3446 .note = "no TSX, deprecated",
3447 .alias = "Icelake-Client-noTSX",
3448 .props = (PropValue[]) {
3449 { "hle", "off" },
3450 { "rtm", "off" },
3451 { /* end of list */ }
3454 { /* end of list */ }
3456 .deprecation_note = "use Icelake-Server instead"
3459 .name = "Icelake-Server",
3460 .level = 0xd,
3461 .vendor = CPUID_VENDOR_INTEL,
3462 .family = 6,
3463 .model = 134,
3464 .stepping = 0,
3465 .features[FEAT_1_EDX] =
3466 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3467 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3468 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3469 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3470 CPUID_DE | CPUID_FP87,
3471 .features[FEAT_1_ECX] =
3472 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3473 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3474 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3475 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3476 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3477 CPUID_EXT_PCID | CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3478 .features[FEAT_8000_0001_EDX] =
3479 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
3480 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3481 .features[FEAT_8000_0001_ECX] =
3482 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3483 .features[FEAT_8000_0008_EBX] =
3484 CPUID_8000_0008_EBX_WBNOINVD,
3485 .features[FEAT_7_0_EBX] =
3486 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 |
3487 CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP |
3488 CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID |
3489 CPUID_7_0_EBX_RTM | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX |
3490 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLWB |
3491 CPUID_7_0_EBX_AVX512F | CPUID_7_0_EBX_AVX512DQ |
3492 CPUID_7_0_EBX_AVX512BW | CPUID_7_0_EBX_AVX512CD |
3493 CPUID_7_0_EBX_AVX512VL | CPUID_7_0_EBX_CLFLUSHOPT,
3494 .features[FEAT_7_0_ECX] =
3495 CPUID_7_0_ECX_AVX512_VBMI | CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_PKU |
3496 CPUID_7_0_ECX_AVX512_VBMI2 | CPUID_7_0_ECX_GFNI |
3497 CPUID_7_0_ECX_VAES | CPUID_7_0_ECX_VPCLMULQDQ |
3498 CPUID_7_0_ECX_AVX512VNNI | CPUID_7_0_ECX_AVX512BITALG |
3499 CPUID_7_0_ECX_AVX512_VPOPCNTDQ | CPUID_7_0_ECX_LA57,
3500 .features[FEAT_7_0_EDX] =
3501 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_SPEC_CTRL_SSBD,
3502 /* Missing: XSAVES (not supported by some Linux versions,
3503 * including v4.1 to v4.12).
3504 * KVM doesn't yet expose any XSAVES state save component,
3505 * and the only one defined in Skylake (processor tracing)
3506 * probably will block migration anyway.
3508 .features[FEAT_XSAVE] =
3509 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3510 CPUID_XSAVE_XGETBV1,
3511 .features[FEAT_6_EAX] =
3512 CPUID_6_EAX_ARAT,
3513 /* Missing: Mode-based execute control (XS/XU), processor tracing, TSC scaling */
3514 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3515 MSR_VMX_BASIC_TRUE_CTLS,
3516 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3517 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3518 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3519 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3520 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3521 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3522 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3523 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3524 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3525 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3526 .features[FEAT_VMX_EXIT_CTLS] =
3527 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3528 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3529 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3530 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3531 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3532 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3533 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3534 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3535 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3536 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3537 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3538 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3539 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3540 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3541 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3542 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3543 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3544 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3545 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3546 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3547 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3548 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3549 .features[FEAT_VMX_SECONDARY_CTLS] =
3550 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3551 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3552 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3553 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3554 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3555 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3556 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3557 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3558 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS,
3559 .xlevel = 0x80000008,
3560 .model_id = "Intel Xeon Processor (Icelake)",
3561 .versions = (X86CPUVersionDefinition[]) {
3562 { .version = 1 },
3564 .version = 2,
3565 .note = "no TSX",
3566 .alias = "Icelake-Server-noTSX",
3567 .props = (PropValue[]) {
3568 { "hle", "off" },
3569 { "rtm", "off" },
3570 { /* end of list */ }
3574 .version = 3,
3575 .props = (PropValue[]) {
3576 { "arch-capabilities", "on" },
3577 { "rdctl-no", "on" },
3578 { "ibrs-all", "on" },
3579 { "skip-l1dfl-vmentry", "on" },
3580 { "mds-no", "on" },
3581 { "pschange-mc-no", "on" },
3582 { "taa-no", "on" },
3583 { /* end of list */ }
3587 .version = 4,
3588 .props = (PropValue[]) {
3589 { "sha-ni", "on" },
3590 { "avx512ifma", "on" },
3591 { "rdpid", "on" },
3592 { "fsrm", "on" },
3593 { "vmx-rdseed-exit", "on" },
3594 { "vmx-pml", "on" },
3595 { "vmx-eptp-switching", "on" },
3596 { "model", "106" },
3597 { /* end of list */ }
3600 { /* end of list */ }
3604 .name = "Denverton",
3605 .level = 21,
3606 .vendor = CPUID_VENDOR_INTEL,
3607 .family = 6,
3608 .model = 95,
3609 .stepping = 1,
3610 .features[FEAT_1_EDX] =
3611 CPUID_FP87 | CPUID_VME | CPUID_DE | CPUID_PSE | CPUID_TSC |
3612 CPUID_MSR | CPUID_PAE | CPUID_MCE | CPUID_CX8 | CPUID_APIC |
3613 CPUID_SEP | CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV |
3614 CPUID_PAT | CPUID_PSE36 | CPUID_CLFLUSH | CPUID_MMX | CPUID_FXSR |
3615 CPUID_SSE | CPUID_SSE2,
3616 .features[FEAT_1_ECX] =
3617 CPUID_EXT_SSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_MONITOR |
3618 CPUID_EXT_SSSE3 | CPUID_EXT_CX16 | CPUID_EXT_SSE41 |
3619 CPUID_EXT_SSE42 | CPUID_EXT_X2APIC | CPUID_EXT_MOVBE |
3620 CPUID_EXT_POPCNT | CPUID_EXT_TSC_DEADLINE_TIMER |
3621 CPUID_EXT_AES | CPUID_EXT_XSAVE | CPUID_EXT_RDRAND,
3622 .features[FEAT_8000_0001_EDX] =
3623 CPUID_EXT2_SYSCALL | CPUID_EXT2_NX | CPUID_EXT2_PDPE1GB |
3624 CPUID_EXT2_RDTSCP | CPUID_EXT2_LM,
3625 .features[FEAT_8000_0001_ECX] =
3626 CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3627 .features[FEAT_7_0_EBX] =
3628 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_ERMS |
3629 CPUID_7_0_EBX_MPX | CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_SMAP |
3630 CPUID_7_0_EBX_CLFLUSHOPT | CPUID_7_0_EBX_SHA_NI,
3631 .features[FEAT_7_0_EDX] =
3632 CPUID_7_0_EDX_SPEC_CTRL | CPUID_7_0_EDX_ARCH_CAPABILITIES |
3633 CPUID_7_0_EDX_SPEC_CTRL_SSBD,
3635 * Missing: XSAVES (not supported by some Linux versions,
3636 * including v4.1 to v4.12).
3637 * KVM doesn't yet expose any XSAVES state save component,
3638 * and the only one defined in Skylake (processor tracing)
3639 * probably will block migration anyway.
3641 .features[FEAT_XSAVE] =
3642 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC | CPUID_XSAVE_XGETBV1,
3643 .features[FEAT_6_EAX] =
3644 CPUID_6_EAX_ARAT,
3645 .features[FEAT_ARCH_CAPABILITIES] =
3646 MSR_ARCH_CAP_RDCL_NO | MSR_ARCH_CAP_SKIP_L1DFL_VMENTRY,
3647 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3648 MSR_VMX_BASIC_TRUE_CTLS,
3649 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3650 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3651 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3652 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3653 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3654 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3655 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3656 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3657 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3658 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3659 .features[FEAT_VMX_EXIT_CTLS] =
3660 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3661 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3662 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3663 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3664 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3665 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3666 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3667 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3668 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3669 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3670 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3671 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3672 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3673 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3674 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3675 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3676 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3677 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3678 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3679 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3680 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3681 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3682 .features[FEAT_VMX_SECONDARY_CTLS] =
3683 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3684 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3685 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3686 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3687 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3688 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3689 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3690 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3691 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3692 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3693 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
3694 .xlevel = 0x80000008,
3695 .model_id = "Intel Atom Processor (Denverton)",
3696 .versions = (X86CPUVersionDefinition[]) {
3697 { .version = 1 },
3699 .version = 2,
3700 .note = "no MPX, no MONITOR",
3701 .props = (PropValue[]) {
3702 { "monitor", "off" },
3703 { "mpx", "off" },
3704 { /* end of list */ },
3707 { /* end of list */ },
3711 .name = "Snowridge",
3712 .level = 27,
3713 .vendor = CPUID_VENDOR_INTEL,
3714 .family = 6,
3715 .model = 134,
3716 .stepping = 1,
3717 .features[FEAT_1_EDX] =
3718 /* missing: CPUID_PN CPUID_IA64 */
3719 /* missing: CPUID_DTS, CPUID_HT, CPUID_TM, CPUID_PBE */
3720 CPUID_FP87 | CPUID_VME | CPUID_DE | CPUID_PSE |
3721 CPUID_TSC | CPUID_MSR | CPUID_PAE | CPUID_MCE |
3722 CPUID_CX8 | CPUID_APIC | CPUID_SEP |
3723 CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV |
3724 CPUID_PAT | CPUID_PSE36 | CPUID_CLFLUSH |
3725 CPUID_MMX |
3726 CPUID_FXSR | CPUID_SSE | CPUID_SSE2,
3727 .features[FEAT_1_ECX] =
3728 CPUID_EXT_SSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_MONITOR |
3729 CPUID_EXT_SSSE3 |
3730 CPUID_EXT_CX16 |
3731 CPUID_EXT_SSE41 |
3732 CPUID_EXT_SSE42 | CPUID_EXT_X2APIC | CPUID_EXT_MOVBE |
3733 CPUID_EXT_POPCNT |
3734 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_AES | CPUID_EXT_XSAVE |
3735 CPUID_EXT_RDRAND,
3736 .features[FEAT_8000_0001_EDX] =
3737 CPUID_EXT2_SYSCALL |
3738 CPUID_EXT2_NX |
3739 CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
3740 CPUID_EXT2_LM,
3741 .features[FEAT_8000_0001_ECX] =
3742 CPUID_EXT3_LAHF_LM |
3743 CPUID_EXT3_3DNOWPREFETCH,
3744 .features[FEAT_7_0_EBX] =
3745 CPUID_7_0_EBX_FSGSBASE |
3746 CPUID_7_0_EBX_SMEP |
3747 CPUID_7_0_EBX_ERMS |
3748 CPUID_7_0_EBX_MPX | /* missing bits 13, 15 */
3749 CPUID_7_0_EBX_RDSEED |
3750 CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT |
3751 CPUID_7_0_EBX_CLWB |
3752 CPUID_7_0_EBX_SHA_NI,
3753 .features[FEAT_7_0_ECX] =
3754 CPUID_7_0_ECX_UMIP |
3755 /* missing bit 5 */
3756 CPUID_7_0_ECX_GFNI |
3757 CPUID_7_0_ECX_MOVDIRI | CPUID_7_0_ECX_CLDEMOTE |
3758 CPUID_7_0_ECX_MOVDIR64B,
3759 .features[FEAT_7_0_EDX] =
3760 CPUID_7_0_EDX_SPEC_CTRL |
3761 CPUID_7_0_EDX_ARCH_CAPABILITIES | CPUID_7_0_EDX_SPEC_CTRL_SSBD |
3762 CPUID_7_0_EDX_CORE_CAPABILITY,
3763 .features[FEAT_CORE_CAPABILITY] =
3764 MSR_CORE_CAP_SPLIT_LOCK_DETECT,
3766 * Missing: XSAVES (not supported by some Linux versions,
3767 * including v4.1 to v4.12).
3768 * KVM doesn't yet expose any XSAVES state save component,
3769 * and the only one defined in Skylake (processor tracing)
3770 * probably will block migration anyway.
3772 .features[FEAT_XSAVE] =
3773 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
3774 CPUID_XSAVE_XGETBV1,
3775 .features[FEAT_6_EAX] =
3776 CPUID_6_EAX_ARAT,
3777 .features[FEAT_VMX_BASIC] = MSR_VMX_BASIC_INS_OUTS |
3778 MSR_VMX_BASIC_TRUE_CTLS,
3779 .features[FEAT_VMX_ENTRY_CTLS] = VMX_VM_ENTRY_IA32E_MODE |
3780 VMX_VM_ENTRY_LOAD_IA32_PERF_GLOBAL_CTRL | VMX_VM_ENTRY_LOAD_IA32_PAT |
3781 VMX_VM_ENTRY_LOAD_DEBUG_CONTROLS | VMX_VM_ENTRY_LOAD_IA32_EFER,
3782 .features[FEAT_VMX_EPT_VPID_CAPS] = MSR_VMX_EPT_EXECONLY |
3783 MSR_VMX_EPT_PAGE_WALK_LENGTH_4 | MSR_VMX_EPT_WB | MSR_VMX_EPT_2MB |
3784 MSR_VMX_EPT_1GB | MSR_VMX_EPT_INVEPT |
3785 MSR_VMX_EPT_INVEPT_SINGLE_CONTEXT | MSR_VMX_EPT_INVEPT_ALL_CONTEXT |
3786 MSR_VMX_EPT_INVVPID | MSR_VMX_EPT_INVVPID_SINGLE_ADDR |
3787 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT | MSR_VMX_EPT_INVVPID_ALL_CONTEXT |
3788 MSR_VMX_EPT_INVVPID_SINGLE_CONTEXT_NOGLOBALS | MSR_VMX_EPT_AD_BITS,
3789 .features[FEAT_VMX_EXIT_CTLS] =
3790 VMX_VM_EXIT_ACK_INTR_ON_EXIT | VMX_VM_EXIT_SAVE_DEBUG_CONTROLS |
3791 VMX_VM_EXIT_LOAD_IA32_PERF_GLOBAL_CTRL |
3792 VMX_VM_EXIT_LOAD_IA32_PAT | VMX_VM_EXIT_LOAD_IA32_EFER |
3793 VMX_VM_EXIT_SAVE_IA32_PAT | VMX_VM_EXIT_SAVE_IA32_EFER |
3794 VMX_VM_EXIT_SAVE_VMX_PREEMPTION_TIMER,
3795 .features[FEAT_VMX_MISC] = MSR_VMX_MISC_ACTIVITY_HLT |
3796 MSR_VMX_MISC_STORE_LMA | MSR_VMX_MISC_VMWRITE_VMEXIT,
3797 .features[FEAT_VMX_PINBASED_CTLS] = VMX_PIN_BASED_EXT_INTR_MASK |
3798 VMX_PIN_BASED_NMI_EXITING | VMX_PIN_BASED_VIRTUAL_NMIS |
3799 VMX_PIN_BASED_VMX_PREEMPTION_TIMER | VMX_PIN_BASED_POSTED_INTR,
3800 .features[FEAT_VMX_PROCBASED_CTLS] = VMX_CPU_BASED_VIRTUAL_INTR_PENDING |
3801 VMX_CPU_BASED_USE_TSC_OFFSETING | VMX_CPU_BASED_HLT_EXITING |
3802 VMX_CPU_BASED_INVLPG_EXITING | VMX_CPU_BASED_MWAIT_EXITING |
3803 VMX_CPU_BASED_RDPMC_EXITING | VMX_CPU_BASED_RDTSC_EXITING |
3804 VMX_CPU_BASED_CR8_LOAD_EXITING | VMX_CPU_BASED_CR8_STORE_EXITING |
3805 VMX_CPU_BASED_TPR_SHADOW | VMX_CPU_BASED_MOV_DR_EXITING |
3806 VMX_CPU_BASED_UNCOND_IO_EXITING | VMX_CPU_BASED_USE_IO_BITMAPS |
3807 VMX_CPU_BASED_MONITOR_EXITING | VMX_CPU_BASED_PAUSE_EXITING |
3808 VMX_CPU_BASED_VIRTUAL_NMI_PENDING | VMX_CPU_BASED_USE_MSR_BITMAPS |
3809 VMX_CPU_BASED_CR3_LOAD_EXITING | VMX_CPU_BASED_CR3_STORE_EXITING |
3810 VMX_CPU_BASED_MONITOR_TRAP_FLAG |
3811 VMX_CPU_BASED_ACTIVATE_SECONDARY_CONTROLS,
3812 .features[FEAT_VMX_SECONDARY_CTLS] =
3813 VMX_SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES |
3814 VMX_SECONDARY_EXEC_WBINVD_EXITING | VMX_SECONDARY_EXEC_ENABLE_EPT |
3815 VMX_SECONDARY_EXEC_DESC | VMX_SECONDARY_EXEC_RDTSCP |
3816 VMX_SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE |
3817 VMX_SECONDARY_EXEC_ENABLE_VPID | VMX_SECONDARY_EXEC_UNRESTRICTED_GUEST |
3818 VMX_SECONDARY_EXEC_APIC_REGISTER_VIRT |
3819 VMX_SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY |
3820 VMX_SECONDARY_EXEC_RDRAND_EXITING | VMX_SECONDARY_EXEC_ENABLE_INVPCID |
3821 VMX_SECONDARY_EXEC_ENABLE_VMFUNC | VMX_SECONDARY_EXEC_SHADOW_VMCS |
3822 VMX_SECONDARY_EXEC_RDSEED_EXITING | VMX_SECONDARY_EXEC_ENABLE_PML,
3823 .features[FEAT_VMX_VMFUNC] = MSR_VMX_VMFUNC_EPT_SWITCHING,
3824 .xlevel = 0x80000008,
3825 .model_id = "Intel Atom Processor (SnowRidge)",
3826 .versions = (X86CPUVersionDefinition[]) {
3827 { .version = 1 },
3829 .version = 2,
3830 .props = (PropValue[]) {
3831 { "mpx", "off" },
3832 { "model-id", "Intel Atom Processor (Snowridge, no MPX)" },
3833 { /* end of list */ },
3836 { /* end of list */ },
3840 .name = "KnightsMill",
3841 .level = 0xd,
3842 .vendor = CPUID_VENDOR_INTEL,
3843 .family = 6,
3844 .model = 133,
3845 .stepping = 0,
3846 .features[FEAT_1_EDX] =
3847 CPUID_VME | CPUID_SS | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR |
3848 CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV |
3849 CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC |
3850 CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC |
3851 CPUID_PSE | CPUID_DE | CPUID_FP87,
3852 .features[FEAT_1_ECX] =
3853 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3854 CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 |
3855 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 |
3856 CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
3857 CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE |
3858 CPUID_EXT_F16C | CPUID_EXT_RDRAND,
3859 .features[FEAT_8000_0001_EDX] =
3860 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP |
3861 CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3862 .features[FEAT_8000_0001_ECX] =
3863 CPUID_EXT3_ABM | CPUID_EXT3_LAHF_LM | CPUID_EXT3_3DNOWPREFETCH,
3864 .features[FEAT_7_0_EBX] =
3865 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
3866 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS |
3867 CPUID_7_0_EBX_RDSEED | CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_AVX512F |
3868 CPUID_7_0_EBX_AVX512CD | CPUID_7_0_EBX_AVX512PF |
3869 CPUID_7_0_EBX_AVX512ER,
3870 .features[FEAT_7_0_ECX] =
3871 CPUID_7_0_ECX_AVX512_VPOPCNTDQ,
3872 .features[FEAT_7_0_EDX] =
3873 CPUID_7_0_EDX_AVX512_4VNNIW | CPUID_7_0_EDX_AVX512_4FMAPS,
3874 .features[FEAT_XSAVE] =
3875 CPUID_XSAVE_XSAVEOPT,
3876 .features[FEAT_6_EAX] =
3877 CPUID_6_EAX_ARAT,
3878 .xlevel = 0x80000008,
3879 .model_id = "Intel Xeon Phi Processor (Knights Mill)",
3882 .name = "Opteron_G1",
3883 .level = 5,
3884 .vendor = CPUID_VENDOR_AMD,
3885 .family = 15,
3886 .model = 6,
3887 .stepping = 1,
3888 .features[FEAT_1_EDX] =
3889 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3890 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3891 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3892 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3893 CPUID_DE | CPUID_FP87,
3894 .features[FEAT_1_ECX] =
3895 CPUID_EXT_SSE3,
3896 .features[FEAT_8000_0001_EDX] =
3897 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3898 .xlevel = 0x80000008,
3899 .model_id = "AMD Opteron 240 (Gen 1 Class Opteron)",
3902 .name = "Opteron_G2",
3903 .level = 5,
3904 .vendor = CPUID_VENDOR_AMD,
3905 .family = 15,
3906 .model = 6,
3907 .stepping = 1,
3908 .features[FEAT_1_EDX] =
3909 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3910 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3911 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3912 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3913 CPUID_DE | CPUID_FP87,
3914 .features[FEAT_1_ECX] =
3915 CPUID_EXT_CX16 | CPUID_EXT_SSE3,
3916 .features[FEAT_8000_0001_EDX] =
3917 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL,
3918 .features[FEAT_8000_0001_ECX] =
3919 CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM,
3920 .xlevel = 0x80000008,
3921 .model_id = "AMD Opteron 22xx (Gen 2 Class Opteron)",
3924 .name = "Opteron_G3",
3925 .level = 5,
3926 .vendor = CPUID_VENDOR_AMD,
3927 .family = 16,
3928 .model = 2,
3929 .stepping = 3,
3930 .features[FEAT_1_EDX] =
3931 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3932 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3933 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3934 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3935 CPUID_DE | CPUID_FP87,
3936 .features[FEAT_1_ECX] =
3937 CPUID_EXT_POPCNT | CPUID_EXT_CX16 | CPUID_EXT_MONITOR |
3938 CPUID_EXT_SSE3,
3939 .features[FEAT_8000_0001_EDX] =
3940 CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL |
3941 CPUID_EXT2_RDTSCP,
3942 .features[FEAT_8000_0001_ECX] =
3943 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A |
3944 CPUID_EXT3_ABM | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM,
3945 .xlevel = 0x80000008,
3946 .model_id = "AMD Opteron 23xx (Gen 3 Class Opteron)",
3949 .name = "Opteron_G4",
3950 .level = 0xd,
3951 .vendor = CPUID_VENDOR_AMD,
3952 .family = 21,
3953 .model = 1,
3954 .stepping = 2,
3955 .features[FEAT_1_EDX] =
3956 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3957 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3958 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3959 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3960 CPUID_DE | CPUID_FP87,
3961 .features[FEAT_1_ECX] =
3962 CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES |
3963 CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
3964 CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ |
3965 CPUID_EXT_SSE3,
3966 .features[FEAT_8000_0001_EDX] =
3967 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_NX |
3968 CPUID_EXT2_SYSCALL | CPUID_EXT2_RDTSCP,
3969 .features[FEAT_8000_0001_ECX] =
3970 CPUID_EXT3_FMA4 | CPUID_EXT3_XOP |
3971 CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_MISALIGNSSE |
3972 CPUID_EXT3_SSE4A | CPUID_EXT3_ABM | CPUID_EXT3_SVM |
3973 CPUID_EXT3_LAHF_LM,
3974 .features[FEAT_SVM] =
3975 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
3976 /* no xsaveopt! */
3977 .xlevel = 0x8000001A,
3978 .model_id = "AMD Opteron 62xx class CPU",
3981 .name = "Opteron_G5",
3982 .level = 0xd,
3983 .vendor = CPUID_VENDOR_AMD,
3984 .family = 21,
3985 .model = 2,
3986 .stepping = 0,
3987 .features[FEAT_1_EDX] =
3988 CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
3989 CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA |
3990 CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 |
3991 CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE |
3992 CPUID_DE | CPUID_FP87,
3993 .features[FEAT_1_ECX] =
3994 CPUID_EXT_F16C | CPUID_EXT_AVX | CPUID_EXT_XSAVE |
3995 CPUID_EXT_AES | CPUID_EXT_POPCNT | CPUID_EXT_SSE42 |
3996 CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_FMA |
3997 CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3,
3998 .features[FEAT_8000_0001_EDX] =
3999 CPUID_EXT2_LM | CPUID_EXT2_PDPE1GB | CPUID_EXT2_NX |
4000 CPUID_EXT2_SYSCALL | CPUID_EXT2_RDTSCP,
4001 .features[FEAT_8000_0001_ECX] =
4002 CPUID_EXT3_TBM | CPUID_EXT3_FMA4 | CPUID_EXT3_XOP |
4003 CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_MISALIGNSSE |
4004 CPUID_EXT3_SSE4A | CPUID_EXT3_ABM | CPUID_EXT3_SVM |
4005 CPUID_EXT3_LAHF_LM,
4006 .features[FEAT_SVM] =
4007 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
4008 /* no xsaveopt! */
4009 .xlevel = 0x8000001A,
4010 .model_id = "AMD Opteron 63xx class CPU",
4013 .name = "EPYC",
4014 .level = 0xd,
4015 .vendor = CPUID_VENDOR_AMD,
4016 .family = 23,
4017 .model = 1,
4018 .stepping = 2,
4019 .features[FEAT_1_EDX] =
4020 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
4021 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
4022 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
4023 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
4024 CPUID_VME | CPUID_FP87,
4025 .features[FEAT_1_ECX] =
4026 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
4027 CPUID_EXT_XSAVE | CPUID_EXT_AES | CPUID_EXT_POPCNT |
4028 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
4029 CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 |
4030 CPUID_EXT_MONITOR | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3,
4031 .features[FEAT_8000_0001_EDX] =
4032 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
4033 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
4034 CPUID_EXT2_SYSCALL,
4035 .features[FEAT_8000_0001_ECX] =
4036 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
4037 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
4038 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
4039 CPUID_EXT3_TOPOEXT,
4040 .features[FEAT_7_0_EBX] =
4041 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
4042 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_RDSEED |
4043 CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT |
4044 CPUID_7_0_EBX_SHA_NI,
4045 .features[FEAT_XSAVE] =
4046 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
4047 CPUID_XSAVE_XGETBV1,
4048 .features[FEAT_6_EAX] =
4049 CPUID_6_EAX_ARAT,
4050 .features[FEAT_SVM] =
4051 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
4052 .xlevel = 0x8000001E,
4053 .model_id = "AMD EPYC Processor",
4054 .cache_info = &epyc_cache_info,
4055 .versions = (X86CPUVersionDefinition[]) {
4056 { .version = 1 },
4058 .version = 2,
4059 .alias = "EPYC-IBPB",
4060 .props = (PropValue[]) {
4061 { "ibpb", "on" },
4062 { "model-id",
4063 "AMD EPYC Processor (with IBPB)" },
4064 { /* end of list */ }
4068 .version = 3,
4069 .props = (PropValue[]) {
4070 { "ibpb", "on" },
4071 { "perfctr-core", "on" },
4072 { "clzero", "on" },
4073 { "xsaveerptr", "on" },
4074 { "xsaves", "on" },
4075 { "model-id",
4076 "AMD EPYC Processor" },
4077 { /* end of list */ }
4080 { /* end of list */ }
4084 .name = "Dhyana",
4085 .level = 0xd,
4086 .vendor = CPUID_VENDOR_HYGON,
4087 .family = 24,
4088 .model = 0,
4089 .stepping = 1,
4090 .features[FEAT_1_EDX] =
4091 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
4092 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
4093 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
4094 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
4095 CPUID_VME | CPUID_FP87,
4096 .features[FEAT_1_ECX] =
4097 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
4098 CPUID_EXT_XSAVE | CPUID_EXT_POPCNT |
4099 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
4100 CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 |
4101 CPUID_EXT_MONITOR | CPUID_EXT_SSE3,
4102 .features[FEAT_8000_0001_EDX] =
4103 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
4104 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
4105 CPUID_EXT2_SYSCALL,
4106 .features[FEAT_8000_0001_ECX] =
4107 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
4108 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
4109 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
4110 CPUID_EXT3_TOPOEXT,
4111 .features[FEAT_8000_0008_EBX] =
4112 CPUID_8000_0008_EBX_IBPB,
4113 .features[FEAT_7_0_EBX] =
4114 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
4115 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_RDSEED |
4116 CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT,
4118 * Missing: XSAVES (not supported by some Linux versions,
4119 * including v4.1 to v4.12).
4120 * KVM doesn't yet expose any XSAVES state save component.
4122 .features[FEAT_XSAVE] =
4123 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
4124 CPUID_XSAVE_XGETBV1,
4125 .features[FEAT_6_EAX] =
4126 CPUID_6_EAX_ARAT,
4127 .features[FEAT_SVM] =
4128 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
4129 .xlevel = 0x8000001E,
4130 .model_id = "Hygon Dhyana Processor",
4131 .cache_info = &epyc_cache_info,
4134 .name = "EPYC-Rome",
4135 .level = 0xd,
4136 .vendor = CPUID_VENDOR_AMD,
4137 .family = 23,
4138 .model = 49,
4139 .stepping = 0,
4140 .features[FEAT_1_EDX] =
4141 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
4142 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
4143 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
4144 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
4145 CPUID_VME | CPUID_FP87,
4146 .features[FEAT_1_ECX] =
4147 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
4148 CPUID_EXT_XSAVE | CPUID_EXT_AES | CPUID_EXT_POPCNT |
4149 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
4150 CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 |
4151 CPUID_EXT_MONITOR | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3,
4152 .features[FEAT_8000_0001_EDX] =
4153 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
4154 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
4155 CPUID_EXT2_SYSCALL,
4156 .features[FEAT_8000_0001_ECX] =
4157 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
4158 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
4159 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
4160 CPUID_EXT3_TOPOEXT | CPUID_EXT3_PERFCORE,
4161 .features[FEAT_8000_0008_EBX] =
4162 CPUID_8000_0008_EBX_CLZERO | CPUID_8000_0008_EBX_XSAVEERPTR |
4163 CPUID_8000_0008_EBX_WBNOINVD | CPUID_8000_0008_EBX_IBPB |
4164 CPUID_8000_0008_EBX_STIBP,
4165 .features[FEAT_7_0_EBX] =
4166 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
4167 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_RDSEED |
4168 CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT |
4169 CPUID_7_0_EBX_SHA_NI | CPUID_7_0_EBX_CLWB,
4170 .features[FEAT_7_0_ECX] =
4171 CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_RDPID,
4172 .features[FEAT_XSAVE] =
4173 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
4174 CPUID_XSAVE_XGETBV1 | CPUID_XSAVE_XSAVES,
4175 .features[FEAT_6_EAX] =
4176 CPUID_6_EAX_ARAT,
4177 .features[FEAT_SVM] =
4178 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE,
4179 .xlevel = 0x8000001E,
4180 .model_id = "AMD EPYC-Rome Processor",
4181 .cache_info = &epyc_rome_cache_info,
4184 .name = "EPYC-Milan",
4185 .level = 0xd,
4186 .vendor = CPUID_VENDOR_AMD,
4187 .family = 25,
4188 .model = 1,
4189 .stepping = 1,
4190 .features[FEAT_1_EDX] =
4191 CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | CPUID_CLFLUSH |
4192 CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | CPUID_PGE |
4193 CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | CPUID_MCE |
4194 CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | CPUID_DE |
4195 CPUID_VME | CPUID_FP87,
4196 .features[FEAT_1_ECX] =
4197 CPUID_EXT_RDRAND | CPUID_EXT_F16C | CPUID_EXT_AVX |
4198 CPUID_EXT_XSAVE | CPUID_EXT_AES | CPUID_EXT_POPCNT |
4199 CPUID_EXT_MOVBE | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 |
4200 CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 |
4201 CPUID_EXT_MONITOR | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 |
4202 CPUID_EXT_PCID,
4203 .features[FEAT_8000_0001_EDX] =
4204 CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_PDPE1GB |
4205 CPUID_EXT2_FFXSR | CPUID_EXT2_MMXEXT | CPUID_EXT2_NX |
4206 CPUID_EXT2_SYSCALL,
4207 .features[FEAT_8000_0001_ECX] =
4208 CPUID_EXT3_OSVW | CPUID_EXT3_3DNOWPREFETCH |
4209 CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM |
4210 CPUID_EXT3_CR8LEG | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM |
4211 CPUID_EXT3_TOPOEXT | CPUID_EXT3_PERFCORE,
4212 .features[FEAT_8000_0008_EBX] =
4213 CPUID_8000_0008_EBX_CLZERO | CPUID_8000_0008_EBX_XSAVEERPTR |
4214 CPUID_8000_0008_EBX_WBNOINVD | CPUID_8000_0008_EBX_IBPB |
4215 CPUID_8000_0008_EBX_IBRS | CPUID_8000_0008_EBX_STIBP |
4216 CPUID_8000_0008_EBX_AMD_SSBD,
4217 .features[FEAT_7_0_EBX] =
4218 CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_AVX2 |
4219 CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_RDSEED |
4220 CPUID_7_0_EBX_ADX | CPUID_7_0_EBX_SMAP | CPUID_7_0_EBX_CLFLUSHOPT |
4221 CPUID_7_0_EBX_SHA_NI | CPUID_7_0_EBX_CLWB | CPUID_7_0_EBX_ERMS |
4222 CPUID_7_0_EBX_INVPCID,
4223 .features[FEAT_7_0_ECX] =
4224 CPUID_7_0_ECX_UMIP | CPUID_7_0_ECX_RDPID | CPUID_7_0_ECX_PKU,
4225 .features[FEAT_7_0_EDX] =
4226 CPUID_7_0_EDX_FSRM,
4227 .features[FEAT_XSAVE] =
4228 CPUID_XSAVE_XSAVEOPT | CPUID_XSAVE_XSAVEC |
4229 CPUID_XSAVE_XGETBV1 | CPUID_XSAVE_XSAVES,
4230 .features[FEAT_6_EAX] =
4231 CPUID_6_EAX_ARAT,
4232 .features[FEAT_SVM] =
4233 CPUID_SVM_NPT | CPUID_SVM_NRIPSAVE | CPUID_SVM_SVME_ADDR_CHK,
4234 .xlevel = 0x8000001E,
4235 .model_id = "AMD EPYC-Milan Processor",
4236 .cache_info = &epyc_milan_cache_info,
4240 /* KVM-specific features that are automatically added/removed
4241 * from all CPU models when KVM is enabled.
4243 static PropValue kvm_default_props[] = {
4244 { "kvmclock", "on" },
4245 { "kvm-nopiodelay", "on" },
4246 { "kvm-asyncpf", "on" },
4247 { "kvm-steal-time", "on" },
4248 { "kvm-pv-eoi", "on" },
4249 { "kvmclock-stable-bit", "on" },
4250 { "x2apic", "on" },
4251 { "kvm-msi-ext-dest-id", "off" },
4252 { "acpi", "off" },
4253 { "monitor", "off" },
4254 { "svm", "off" },
4255 { NULL, NULL },
4258 /* TCG-specific defaults that override all CPU models when using TCG
4260 static PropValue tcg_default_props[] = {
4261 { "vme", "off" },
4262 { NULL, NULL },
4267 * We resolve CPU model aliases using -v1 when using "-machine
4268 * none", but this is just for compatibility while libvirt isn't
4269 * adapted to resolve CPU model versions before creating VMs.
4270 * See "Runnability guarantee of CPU models" at
4271 * docs/system/deprecated.rst.
4273 X86CPUVersion default_cpu_version = 1;
4275 void x86_cpu_set_default_version(X86CPUVersion version)
4277 /* Translating CPU_VERSION_AUTO to CPU_VERSION_AUTO doesn't make sense */
4278 assert(version != CPU_VERSION_AUTO);
4279 default_cpu_version = version;
4282 static X86CPUVersion x86_cpu_model_last_version(const X86CPUModel *model)
4284 int v = 0;
4285 const X86CPUVersionDefinition *vdef =
4286 x86_cpu_def_get_versions(model->cpudef);
4287 while (vdef->version) {
4288 v = vdef->version;
4289 vdef++;
4291 return v;
4294 /* Return the actual version being used for a specific CPU model */
4295 static X86CPUVersion x86_cpu_model_resolve_version(const X86CPUModel *model)
4297 X86CPUVersion v = model->version;
4298 if (v == CPU_VERSION_AUTO) {
4299 v = default_cpu_version;
4301 if (v == CPU_VERSION_LATEST) {
4302 return x86_cpu_model_last_version(model);
4304 return v;
4307 void x86_cpu_change_kvm_default(const char *prop, const char *value)
4309 PropValue *pv;
4310 for (pv = kvm_default_props; pv->prop; pv++) {
4311 if (!strcmp(pv->prop, prop)) {
4312 pv->value = value;
4313 break;
4317 /* It is valid to call this function only for properties that
4318 * are already present in the kvm_default_props table.
4320 assert(pv->prop);
4323 static bool lmce_supported(void)
4325 uint64_t mce_cap = 0;
4327 #ifdef CONFIG_KVM
4328 if (kvm_ioctl(kvm_state, KVM_X86_GET_MCE_CAP_SUPPORTED, &mce_cap) < 0) {
4329 return false;
4331 #endif
4333 return !!(mce_cap & MCG_LMCE_P);
4336 #define CPUID_MODEL_ID_SZ 48
4339 * cpu_x86_fill_model_id:
4340 * Get CPUID model ID string from host CPU.
4342 * @str should have at least CPUID_MODEL_ID_SZ bytes
4344 * The function does NOT add a null terminator to the string
4345 * automatically.
4347 static int cpu_x86_fill_model_id(char *str)
4349 uint32_t eax = 0, ebx = 0, ecx = 0, edx = 0;
4350 int i;
4352 for (i = 0; i < 3; i++) {
4353 host_cpuid(0x80000002 + i, 0, &eax, &ebx, &ecx, &edx);
4354 memcpy(str + i * 16 + 0, &eax, 4);
4355 memcpy(str + i * 16 + 4, &ebx, 4);
4356 memcpy(str + i * 16 + 8, &ecx, 4);
4357 memcpy(str + i * 16 + 12, &edx, 4);
4359 return 0;
4362 static Property max_x86_cpu_properties[] = {
4363 DEFINE_PROP_BOOL("migratable", X86CPU, migratable, true),
4364 DEFINE_PROP_BOOL("host-cache-info", X86CPU, cache_info_passthrough, false),
4365 DEFINE_PROP_END_OF_LIST()
4368 static void max_x86_cpu_class_init(ObjectClass *oc, void *data)
4370 DeviceClass *dc = DEVICE_CLASS(oc);
4371 X86CPUClass *xcc = X86_CPU_CLASS(oc);
4373 xcc->ordering = 9;
4375 xcc->model_description =
4376 "Enables all features supported by the accelerator in the current host";
4378 device_class_set_props(dc, max_x86_cpu_properties);
4381 static void max_x86_cpu_initfn(Object *obj)
4383 X86CPU *cpu = X86_CPU(obj);
4384 CPUX86State *env = &cpu->env;
4385 KVMState *s = kvm_state;
4387 /* We can't fill the features array here because we don't know yet if
4388 * "migratable" is true or false.
4390 cpu->max_features = true;
4392 if (accel_uses_host_cpuid()) {
4393 char vendor[CPUID_VENDOR_SZ + 1] = { 0 };
4394 char model_id[CPUID_MODEL_ID_SZ + 1] = { 0 };
4395 int family, model, stepping;
4397 host_vendor_fms(vendor, &family, &model, &stepping);
4398 cpu_x86_fill_model_id(model_id);
4400 object_property_set_str(OBJECT(cpu), "vendor", vendor, &error_abort);
4401 object_property_set_int(OBJECT(cpu), "family", family, &error_abort);
4402 object_property_set_int(OBJECT(cpu), "model", model, &error_abort);
4403 object_property_set_int(OBJECT(cpu), "stepping", stepping,
4404 &error_abort);
4405 object_property_set_str(OBJECT(cpu), "model-id", model_id,
4406 &error_abort);
4408 if (kvm_enabled()) {
4409 env->cpuid_min_level =
4410 kvm_arch_get_supported_cpuid(s, 0x0, 0, R_EAX);
4411 env->cpuid_min_xlevel =
4412 kvm_arch_get_supported_cpuid(s, 0x80000000, 0, R_EAX);
4413 env->cpuid_min_xlevel2 =
4414 kvm_arch_get_supported_cpuid(s, 0xC0000000, 0, R_EAX);
4415 } else {
4416 env->cpuid_min_level =
4417 hvf_get_supported_cpuid(0x0, 0, R_EAX);
4418 env->cpuid_min_xlevel =
4419 hvf_get_supported_cpuid(0x80000000, 0, R_EAX);
4420 env->cpuid_min_xlevel2 =
4421 hvf_get_supported_cpuid(0xC0000000, 0, R_EAX);
4424 if (lmce_supported()) {
4425 object_property_set_bool(OBJECT(cpu), "lmce", true, &error_abort);
4427 object_property_set_bool(OBJECT(cpu), "host-phys-bits", true, &error_abort);
4428 } else {
4429 object_property_set_str(OBJECT(cpu), "vendor", CPUID_VENDOR_AMD,
4430 &error_abort);
4431 object_property_set_int(OBJECT(cpu), "family", 6, &error_abort);
4432 object_property_set_int(OBJECT(cpu), "model", 6, &error_abort);
4433 object_property_set_int(OBJECT(cpu), "stepping", 3, &error_abort);
4434 object_property_set_str(OBJECT(cpu), "model-id",
4435 "QEMU TCG CPU version " QEMU_HW_VERSION,
4436 &error_abort);
4439 object_property_set_bool(OBJECT(cpu), "pmu", true, &error_abort);
4442 static const TypeInfo max_x86_cpu_type_info = {
4443 .name = X86_CPU_TYPE_NAME("max"),
4444 .parent = TYPE_X86_CPU,
4445 .instance_init = max_x86_cpu_initfn,
4446 .class_init = max_x86_cpu_class_init,
4449 #if defined(CONFIG_KVM) || defined(CONFIG_HVF)
4450 static void host_x86_cpu_class_init(ObjectClass *oc, void *data)
4452 X86CPUClass *xcc = X86_CPU_CLASS(oc);
4454 xcc->host_cpuid_required = true;
4455 xcc->ordering = 8;
4457 #if defined(CONFIG_KVM)
4458 xcc->model_description =
4459 "KVM processor with all supported host features ";
4460 #elif defined(CONFIG_HVF)
4461 xcc->model_description =
4462 "HVF processor with all supported host features ";
4463 #endif
4466 static const TypeInfo host_x86_cpu_type_info = {
4467 .name = X86_CPU_TYPE_NAME("host"),
4468 .parent = X86_CPU_TYPE_NAME("max"),
4469 .class_init = host_x86_cpu_class_init,
4472 #endif
4474 static char *feature_word_description(FeatureWordInfo *f, uint32_t bit)
4476 assert(f->type == CPUID_FEATURE_WORD || f->type == MSR_FEATURE_WORD);
4478 switch (f->type) {
4479 case CPUID_FEATURE_WORD:
4481 const char *reg = get_register_name_32(f->cpuid.reg);
4482 assert(reg);
4483 return g_strdup_printf("CPUID.%02XH:%s",
4484 f->cpuid.eax, reg);
4486 case MSR_FEATURE_WORD:
4487 return g_strdup_printf("MSR(%02XH)",
4488 f->msr.index);
4491 return NULL;
4494 static bool x86_cpu_have_filtered_features(X86CPU *cpu)
4496 FeatureWord w;
4498 for (w = 0; w < FEATURE_WORDS; w++) {
4499 if (cpu->filtered_features[w]) {
4500 return true;
4504 return false;
4507 static void mark_unavailable_features(X86CPU *cpu, FeatureWord w, uint64_t mask,
4508 const char *verbose_prefix)
4510 CPUX86State *env = &cpu->env;
4511 FeatureWordInfo *f = &feature_word_info[w];
4512 int i;
4514 if (!cpu->force_features) {
4515 env->features[w] &= ~mask;
4517 cpu->filtered_features[w] |= mask;
4519 if (!verbose_prefix) {
4520 return;
4523 for (i = 0; i < 64; ++i) {
4524 if ((1ULL << i) & mask) {
4525 g_autofree char *feat_word_str = feature_word_description(f, i);
4526 warn_report("%s: %s%s%s [bit %d]",
4527 verbose_prefix,
4528 feat_word_str,
4529 f->feat_names[i] ? "." : "",
4530 f->feat_names[i] ? f->feat_names[i] : "", i);
4535 static void x86_cpuid_version_get_family(Object *obj, Visitor *v,
4536 const char *name, void *opaque,
4537 Error **errp)
4539 X86CPU *cpu = X86_CPU(obj);
4540 CPUX86State *env = &cpu->env;
4541 int64_t value;
4543 value = (env->cpuid_version >> 8) & 0xf;
4544 if (value == 0xf) {
4545 value += (env->cpuid_version >> 20) & 0xff;
4547 visit_type_int(v, name, &value, errp);
4550 static void x86_cpuid_version_set_family(Object *obj, Visitor *v,
4551 const char *name, void *opaque,
4552 Error **errp)
4554 X86CPU *cpu = X86_CPU(obj);
4555 CPUX86State *env = &cpu->env;
4556 const int64_t min = 0;
4557 const int64_t max = 0xff + 0xf;
4558 int64_t value;
4560 if (!visit_type_int(v, name, &value, errp)) {
4561 return;
4563 if (value < min || value > max) {
4564 error_setg(errp, QERR_PROPERTY_VALUE_OUT_OF_RANGE, "",
4565 name ? name : "null", value, min, max);
4566 return;
4569 env->cpuid_version &= ~0xff00f00;
4570 if (value > 0x0f) {
4571 env->cpuid_version |= 0xf00 | ((value - 0x0f) << 20);
4572 } else {
4573 env->cpuid_version |= value << 8;
4577 static void x86_cpuid_version_get_model(Object *obj, Visitor *v,
4578 const char *name, void *opaque,
4579 Error **errp)
4581 X86CPU *cpu = X86_CPU(obj);
4582 CPUX86State *env = &cpu->env;
4583 int64_t value;
4585 value = (env->cpuid_version >> 4) & 0xf;
4586 value |= ((env->cpuid_version >> 16) & 0xf) << 4;
4587 visit_type_int(v, name, &value, errp);
4590 static void x86_cpuid_version_set_model(Object *obj, Visitor *v,
4591 const char *name, void *opaque,
4592 Error **errp)
4594 X86CPU *cpu = X86_CPU(obj);
4595 CPUX86State *env = &cpu->env;
4596 const int64_t min = 0;
4597 const int64_t max = 0xff;
4598 int64_t value;
4600 if (!visit_type_int(v, name, &value, errp)) {
4601 return;
4603 if (value < min || value > max) {
4604 error_setg(errp, QERR_PROPERTY_VALUE_OUT_OF_RANGE, "",
4605 name ? name : "null", value, min, max);
4606 return;
4609 env->cpuid_version &= ~0xf00f0;
4610 env->cpuid_version |= ((value & 0xf) << 4) | ((value >> 4) << 16);
4613 static void x86_cpuid_version_get_stepping(Object *obj, Visitor *v,
4614 const char *name, void *opaque,
4615 Error **errp)
4617 X86CPU *cpu = X86_CPU(obj);
4618 CPUX86State *env = &cpu->env;
4619 int64_t value;
4621 value = env->cpuid_version & 0xf;
4622 visit_type_int(v, name, &value, errp);
4625 static void x86_cpuid_version_set_stepping(Object *obj, Visitor *v,
4626 const char *name, void *opaque,
4627 Error **errp)
4629 X86CPU *cpu = X86_CPU(obj);
4630 CPUX86State *env = &cpu->env;
4631 const int64_t min = 0;
4632 const int64_t max = 0xf;
4633 int64_t value;
4635 if (!visit_type_int(v, name, &value, errp)) {
4636 return;
4638 if (value < min || value > max) {
4639 error_setg(errp, QERR_PROPERTY_VALUE_OUT_OF_RANGE, "",
4640 name ? name : "null", value, min, max);
4641 return;
4644 env->cpuid_version &= ~0xf;
4645 env->cpuid_version |= value & 0xf;
4648 static char *x86_cpuid_get_vendor(Object *obj, Error **errp)
4650 X86CPU *cpu = X86_CPU(obj);
4651 CPUX86State *env = &cpu->env;
4652 char *value;
4654 value = g_malloc(CPUID_VENDOR_SZ + 1);
4655 x86_cpu_vendor_words2str(value, env->cpuid_vendor1, env->cpuid_vendor2,
4656 env->cpuid_vendor3);
4657 return value;
4660 static void x86_cpuid_set_vendor(Object *obj, const char *value,
4661 Error **errp)
4663 X86CPU *cpu = X86_CPU(obj);
4664 CPUX86State *env = &cpu->env;
4665 int i;
4667 if (strlen(value) != CPUID_VENDOR_SZ) {
4668 error_setg(errp, QERR_PROPERTY_VALUE_BAD, "", "vendor", value);
4669 return;
4672 env->cpuid_vendor1 = 0;
4673 env->cpuid_vendor2 = 0;
4674 env->cpuid_vendor3 = 0;
4675 for (i = 0; i < 4; i++) {
4676 env->cpuid_vendor1 |= ((uint8_t)value[i ]) << (8 * i);
4677 env->cpuid_vendor2 |= ((uint8_t)value[i + 4]) << (8 * i);
4678 env->cpuid_vendor3 |= ((uint8_t)value[i + 8]) << (8 * i);
4682 static char *x86_cpuid_get_model_id(Object *obj, Error **errp)
4684 X86CPU *cpu = X86_CPU(obj);
4685 CPUX86State *env = &cpu->env;
4686 char *value;
4687 int i;
4689 value = g_malloc(48 + 1);
4690 for (i = 0; i < 48; i++) {
4691 value[i] = env->cpuid_model[i >> 2] >> (8 * (i & 3));
4693 value[48] = '\0';
4694 return value;
4697 static void x86_cpuid_set_model_id(Object *obj, const char *model_id,
4698 Error **errp)
4700 X86CPU *cpu = X86_CPU(obj);
4701 CPUX86State *env = &cpu->env;
4702 int c, len, i;
4704 if (model_id == NULL) {
4705 model_id = "";
4707 len = strlen(model_id);
4708 memset(env->cpuid_model, 0, 48);
4709 for (i = 0; i < 48; i++) {
4710 if (i >= len) {
4711 c = '\0';
4712 } else {
4713 c = (uint8_t)model_id[i];
4715 env->cpuid_model[i >> 2] |= c << (8 * (i & 3));
4719 static void x86_cpuid_get_tsc_freq(Object *obj, Visitor *v, const char *name,
4720 void *opaque, Error **errp)
4722 X86CPU *cpu = X86_CPU(obj);
4723 int64_t value;
4725 value = cpu->env.tsc_khz * 1000;
4726 visit_type_int(v, name, &value, errp);
4729 static void x86_cpuid_set_tsc_freq(Object *obj, Visitor *v, const char *name,
4730 void *opaque, Error **errp)
4732 X86CPU *cpu = X86_CPU(obj);
4733 const int64_t min = 0;
4734 const int64_t max = INT64_MAX;
4735 int64_t value;
4737 if (!visit_type_int(v, name, &value, errp)) {
4738 return;
4740 if (value < min || value > max) {
4741 error_setg(errp, QERR_PROPERTY_VALUE_OUT_OF_RANGE, "",
4742 name ? name : "null", value, min, max);
4743 return;
4746 cpu->env.tsc_khz = cpu->env.user_tsc_khz = value / 1000;
4749 /* Generic getter for "feature-words" and "filtered-features" properties */
4750 static void x86_cpu_get_feature_words(Object *obj, Visitor *v,
4751 const char *name, void *opaque,
4752 Error **errp)
4754 uint64_t *array = (uint64_t *)opaque;
4755 FeatureWord w;
4756 X86CPUFeatureWordInfo word_infos[FEATURE_WORDS] = { };
4757 X86CPUFeatureWordInfoList list_entries[FEATURE_WORDS] = { };
4758 X86CPUFeatureWordInfoList *list = NULL;
4760 for (w = 0; w < FEATURE_WORDS; w++) {
4761 FeatureWordInfo *wi = &feature_word_info[w];
4763 * We didn't have MSR features when "feature-words" was
4764 * introduced. Therefore skipped other type entries.
4766 if (wi->type != CPUID_FEATURE_WORD) {
4767 continue;
4769 X86CPUFeatureWordInfo *qwi = &word_infos[w];
4770 qwi->cpuid_input_eax = wi->cpuid.eax;
4771 qwi->has_cpuid_input_ecx = wi->cpuid.needs_ecx;
4772 qwi->cpuid_input_ecx = wi->cpuid.ecx;
4773 qwi->cpuid_register = x86_reg_info_32[wi->cpuid.reg].qapi_enum;
4774 qwi->features = array[w];
4776 /* List will be in reverse order, but order shouldn't matter */
4777 list_entries[w].next = list;
4778 list_entries[w].value = &word_infos[w];
4779 list = &list_entries[w];
4782 visit_type_X86CPUFeatureWordInfoList(v, "feature-words", &list, errp);
4785 /* Convert all '_' in a feature string option name to '-', to make feature
4786 * name conform to QOM property naming rule, which uses '-' instead of '_'.
4788 static inline void feat2prop(char *s)
4790 while ((s = strchr(s, '_'))) {
4791 *s = '-';
4795 /* Return the feature property name for a feature flag bit */
4796 static const char *x86_cpu_feature_name(FeatureWord w, int bitnr)
4798 const char *name;
4799 /* XSAVE components are automatically enabled by other features,
4800 * so return the original feature name instead
4802 if (w == FEAT_XSAVE_COMP_LO || w == FEAT_XSAVE_COMP_HI) {
4803 int comp = (w == FEAT_XSAVE_COMP_HI) ? bitnr + 32 : bitnr;
4805 if (comp < ARRAY_SIZE(x86_ext_save_areas) &&
4806 x86_ext_save_areas[comp].bits) {
4807 w = x86_ext_save_areas[comp].feature;
4808 bitnr = ctz32(x86_ext_save_areas[comp].bits);
4812 assert(bitnr < 64);
4813 assert(w < FEATURE_WORDS);
4814 name = feature_word_info[w].feat_names[bitnr];
4815 assert(bitnr < 32 || !(name && feature_word_info[w].type == CPUID_FEATURE_WORD));
4816 return name;
4819 /* Compatibily hack to maintain legacy +-feat semantic,
4820 * where +-feat overwrites any feature set by
4821 * feat=on|feat even if the later is parsed after +-feat
4822 * (i.e. "-x2apic,x2apic=on" will result in x2apic disabled)
4824 static GList *plus_features, *minus_features;
4826 static gint compare_string(gconstpointer a, gconstpointer b)
4828 return g_strcmp0(a, b);
4831 /* Parse "+feature,-feature,feature=foo" CPU feature string
4833 static void x86_cpu_parse_featurestr(const char *typename, char *features,
4834 Error **errp)
4836 char *featurestr; /* Single 'key=value" string being parsed */
4837 static bool cpu_globals_initialized;
4838 bool ambiguous = false;
4840 if (cpu_globals_initialized) {
4841 return;
4843 cpu_globals_initialized = true;
4845 if (!features) {
4846 return;
4849 for (featurestr = strtok(features, ",");
4850 featurestr;
4851 featurestr = strtok(NULL, ",")) {
4852 const char *name;
4853 const char *val = NULL;
4854 char *eq = NULL;
4855 char num[32];
4856 GlobalProperty *prop;
4858 /* Compatibility syntax: */
4859 if (featurestr[0] == '+') {
4860 plus_features = g_list_append(plus_features,
4861 g_strdup(featurestr + 1));
4862 continue;
4863 } else if (featurestr[0] == '-') {
4864 minus_features = g_list_append(minus_features,
4865 g_strdup(featurestr + 1));
4866 continue;
4869 eq = strchr(featurestr, '=');
4870 if (eq) {
4871 *eq++ = 0;
4872 val = eq;
4873 } else {
4874 val = "on";
4877 feat2prop(featurestr);
4878 name = featurestr;
4880 if (g_list_find_custom(plus_features, name, compare_string)) {
4881 warn_report("Ambiguous CPU model string. "
4882 "Don't mix both \"+%s\" and \"%s=%s\"",
4883 name, name, val);
4884 ambiguous = true;
4886 if (g_list_find_custom(minus_features, name, compare_string)) {
4887 warn_report("Ambiguous CPU model string. "
4888 "Don't mix both \"-%s\" and \"%s=%s\"",
4889 name, name, val);
4890 ambiguous = true;
4893 /* Special case: */
4894 if (!strcmp(name, "tsc-freq")) {
4895 int ret;
4896 uint64_t tsc_freq;
4898 ret = qemu_strtosz_metric(val, NULL, &tsc_freq);
4899 if (ret < 0 || tsc_freq > INT64_MAX) {
4900 error_setg(errp, "bad numerical value %s", val);
4901 return;
4903 snprintf(num, sizeof(num), "%" PRId64, tsc_freq);
4904 val = num;
4905 name = "tsc-frequency";
4908 prop = g_new0(typeof(*prop), 1);
4909 prop->driver = typename;
4910 prop->property = g_strdup(name);
4911 prop->value = g_strdup(val);
4912 qdev_prop_register_global(prop);
4915 if (ambiguous) {
4916 warn_report("Compatibility of ambiguous CPU model "
4917 "strings won't be kept on future QEMU versions");
4921 static void x86_cpu_expand_features(X86CPU *cpu, Error **errp);
4922 static void x86_cpu_filter_features(X86CPU *cpu, bool verbose);
4924 /* Build a list with the name of all features on a feature word array */
4925 static void x86_cpu_list_feature_names(FeatureWordArray features,
4926 strList **list)
4928 strList **tail = list;
4929 FeatureWord w;
4931 for (w = 0; w < FEATURE_WORDS; w++) {
4932 uint64_t filtered = features[w];
4933 int i;
4934 for (i = 0; i < 64; i++) {
4935 if (filtered & (1ULL << i)) {
4936 QAPI_LIST_APPEND(tail, g_strdup(x86_cpu_feature_name(w, i)));
4942 static void x86_cpu_get_unavailable_features(Object *obj, Visitor *v,
4943 const char *name, void *opaque,
4944 Error **errp)
4946 X86CPU *xc = X86_CPU(obj);
4947 strList *result = NULL;
4949 x86_cpu_list_feature_names(xc->filtered_features, &result);
4950 visit_type_strList(v, "unavailable-features", &result, errp);
4953 /* Check for missing features that may prevent the CPU class from
4954 * running using the current machine and accelerator.
4956 static void x86_cpu_class_check_missing_features(X86CPUClass *xcc,
4957 strList **list)
4959 strList **tail = list;
4960 X86CPU *xc;
4961 Error *err = NULL;
4963 if (xcc->host_cpuid_required && !accel_uses_host_cpuid()) {
4964 QAPI_LIST_APPEND(tail, g_strdup("kvm"));
4965 return;
4968 xc = X86_CPU(object_new_with_class(OBJECT_CLASS(xcc)));
4970 x86_cpu_expand_features(xc, &err);
4971 if (err) {
4972 /* Errors at x86_cpu_expand_features should never happen,
4973 * but in case it does, just report the model as not
4974 * runnable at all using the "type" property.
4976 QAPI_LIST_APPEND(tail, g_strdup("type"));
4977 error_free(err);
4980 x86_cpu_filter_features(xc, false);
4982 x86_cpu_list_feature_names(xc->filtered_features, tail);
4984 object_unref(OBJECT(xc));
4987 /* Print all cpuid feature names in featureset
4989 static void listflags(GList *features)
4991 size_t len = 0;
4992 GList *tmp;
4994 for (tmp = features; tmp; tmp = tmp->next) {
4995 const char *name = tmp->data;
4996 if ((len + strlen(name) + 1) >= 75) {
4997 qemu_printf("\n");
4998 len = 0;
5000 qemu_printf("%s%s", len == 0 ? " " : " ", name);
5001 len += strlen(name) + 1;
5003 qemu_printf("\n");
5006 /* Sort alphabetically by type name, respecting X86CPUClass::ordering. */
5007 static gint x86_cpu_list_compare(gconstpointer a, gconstpointer b)
5009 ObjectClass *class_a = (ObjectClass *)a;
5010 ObjectClass *class_b = (ObjectClass *)b;
5011 X86CPUClass *cc_a = X86_CPU_CLASS(class_a);
5012 X86CPUClass *cc_b = X86_CPU_CLASS(class_b);
5013 int ret;
5015 if (cc_a->ordering != cc_b->ordering) {
5016 ret = cc_a->ordering - cc_b->ordering;
5017 } else {
5018 g_autofree char *name_a = x86_cpu_class_get_model_name(cc_a);
5019 g_autofree char *name_b = x86_cpu_class_get_model_name(cc_b);
5020 ret = strcmp(name_a, name_b);
5022 return ret;
5025 static GSList *get_sorted_cpu_model_list(void)
5027 GSList *list = object_class_get_list(TYPE_X86_CPU, false);
5028 list = g_slist_sort(list, x86_cpu_list_compare);
5029 return list;
5032 static char *x86_cpu_class_get_model_id(X86CPUClass *xc)
5034 Object *obj = object_new_with_class(OBJECT_CLASS(xc));
5035 char *r = object_property_get_str(obj, "model-id", &error_abort);
5036 object_unref(obj);
5037 return r;
5040 static char *x86_cpu_class_get_alias_of(X86CPUClass *cc)
5042 X86CPUVersion version;
5044 if (!cc->model || !cc->model->is_alias) {
5045 return NULL;
5047 version = x86_cpu_model_resolve_version(cc->model);
5048 if (version <= 0) {
5049 return NULL;
5051 return x86_cpu_versioned_model_name(cc->model->cpudef, version);
5054 static void x86_cpu_list_entry(gpointer data, gpointer user_data)
5056 ObjectClass *oc = data;
5057 X86CPUClass *cc = X86_CPU_CLASS(oc);
5058 g_autofree char *name = x86_cpu_class_get_model_name(cc);
5059 g_autofree char *desc = g_strdup(cc->model_description);
5060 g_autofree char *alias_of = x86_cpu_class_get_alias_of(cc);
5061 g_autofree char *model_id = x86_cpu_class_get_model_id(cc);
5063 if (!desc && alias_of) {
5064 if (cc->model && cc->model->version == CPU_VERSION_AUTO) {
5065 desc = g_strdup("(alias configured by machine type)");
5066 } else {
5067 desc = g_strdup_printf("(alias of %s)", alias_of);
5070 if (!desc && cc->model && cc->model->note) {
5071 desc = g_strdup_printf("%s [%s]", model_id, cc->model->note);
5073 if (!desc) {
5074 desc = g_strdup_printf("%s", model_id);
5077 qemu_printf("x86 %-20s %-58s\n", name, desc);
5080 /* list available CPU models and flags */
5081 void x86_cpu_list(void)
5083 int i, j;
5084 GSList *list;
5085 GList *names = NULL;
5087 qemu_printf("Available CPUs:\n");
5088 list = get_sorted_cpu_model_list();
5089 g_slist_foreach(list, x86_cpu_list_entry, NULL);
5090 g_slist_free(list);
5092 names = NULL;
5093 for (i = 0; i < ARRAY_SIZE(feature_word_info); i++) {
5094 FeatureWordInfo *fw = &feature_word_info[i];
5095 for (j = 0; j < 64; j++) {
5096 if (fw->feat_names[j]) {
5097 names = g_list_append(names, (gpointer)fw->feat_names[j]);
5102 names = g_list_sort(names, (GCompareFunc)strcmp);
5104 qemu_printf("\nRecognized CPUID flags:\n");
5105 listflags(names);
5106 qemu_printf("\n");
5107 g_list_free(names);
5110 static void x86_cpu_definition_entry(gpointer data, gpointer user_data)
5112 ObjectClass *oc = data;
5113 X86CPUClass *cc = X86_CPU_CLASS(oc);
5114 CpuDefinitionInfoList **cpu_list = user_data;
5115 CpuDefinitionInfo *info;
5117 info = g_malloc0(sizeof(*info));
5118 info->name = x86_cpu_class_get_model_name(cc);
5119 x86_cpu_class_check_missing_features(cc, &info->unavailable_features);
5120 info->has_unavailable_features = true;
5121 info->q_typename = g_strdup(object_class_get_name(oc));
5122 info->migration_safe = cc->migration_safe;
5123 info->has_migration_safe = true;
5124 info->q_static = cc->static_model;
5125 if (cc->model && cc->model->cpudef->deprecation_note) {
5126 info->deprecated = true;
5127 } else {
5128 info->deprecated = false;
5131 * Old machine types won't report aliases, so that alias translation
5132 * doesn't break compatibility with previous QEMU versions.
5134 if (default_cpu_version != CPU_VERSION_LEGACY) {
5135 info->alias_of = x86_cpu_class_get_alias_of(cc);
5136 info->has_alias_of = !!info->alias_of;
5139 QAPI_LIST_PREPEND(*cpu_list, info);
5142 CpuDefinitionInfoList *qmp_query_cpu_definitions(Error **errp)
5144 CpuDefinitionInfoList *cpu_list = NULL;
5145 GSList *list = get_sorted_cpu_model_list();
5146 g_slist_foreach(list, x86_cpu_definition_entry, &cpu_list);
5147 g_slist_free(list);
5148 return cpu_list;
5151 static uint64_t x86_cpu_get_supported_feature_word(FeatureWord w,
5152 bool migratable_only)
5154 FeatureWordInfo *wi = &feature_word_info[w];
5155 uint64_t r = 0;
5157 if (kvm_enabled()) {
5158 switch (wi->type) {
5159 case CPUID_FEATURE_WORD:
5160 r = kvm_arch_get_supported_cpuid(kvm_state, wi->cpuid.eax,
5161 wi->cpuid.ecx,
5162 wi->cpuid.reg);
5163 break;
5164 case MSR_FEATURE_WORD:
5165 r = kvm_arch_get_supported_msr_feature(kvm_state,
5166 wi->msr.index);
5167 break;
5169 } else if (hvf_enabled()) {
5170 if (wi->type != CPUID_FEATURE_WORD) {
5171 return 0;
5173 r = hvf_get_supported_cpuid(wi->cpuid.eax,
5174 wi->cpuid.ecx,
5175 wi->cpuid.reg);
5176 } else if (tcg_enabled()) {
5177 r = wi->tcg_features;
5178 } else {
5179 return ~0;
5181 #ifndef TARGET_X86_64
5182 if (w == FEAT_8000_0001_EDX) {
5183 r &= ~CPUID_EXT2_LM;
5185 #endif
5186 if (migratable_only) {
5187 r &= x86_cpu_get_migratable_flags(w);
5189 return r;
5192 static void x86_cpu_apply_props(X86CPU *cpu, PropValue *props)
5194 PropValue *pv;
5195 for (pv = props; pv->prop; pv++) {
5196 if (!pv->value) {
5197 continue;
5199 object_property_parse(OBJECT(cpu), pv->prop, pv->value,
5200 &error_abort);
5204 /* Apply properties for the CPU model version specified in model */
5205 static void x86_cpu_apply_version_props(X86CPU *cpu, X86CPUModel *model)
5207 const X86CPUVersionDefinition *vdef;
5208 X86CPUVersion version = x86_cpu_model_resolve_version(model);
5210 if (version == CPU_VERSION_LEGACY) {
5211 return;
5214 for (vdef = x86_cpu_def_get_versions(model->cpudef); vdef->version; vdef++) {
5215 PropValue *p;
5217 for (p = vdef->props; p && p->prop; p++) {
5218 object_property_parse(OBJECT(cpu), p->prop, p->value,
5219 &error_abort);
5222 if (vdef->version == version) {
5223 break;
5228 * If we reached the end of the list, version number was invalid
5230 assert(vdef->version == version);
5233 /* Load data from X86CPUDefinition into a X86CPU object
5235 static void x86_cpu_load_model(X86CPU *cpu, X86CPUModel *model)
5237 X86CPUDefinition *def = model->cpudef;
5238 CPUX86State *env = &cpu->env;
5239 const char *vendor;
5240 char host_vendor[CPUID_VENDOR_SZ + 1];
5241 FeatureWord w;
5243 /*NOTE: any property set by this function should be returned by
5244 * x86_cpu_static_props(), so static expansion of
5245 * query-cpu-model-expansion is always complete.
5248 /* CPU models only set _minimum_ values for level/xlevel: */
5249 object_property_set_uint(OBJECT(cpu), "min-level", def->level,
5250 &error_abort);
5251 object_property_set_uint(OBJECT(cpu), "min-xlevel", def->xlevel,
5252 &error_abort);
5254 object_property_set_int(OBJECT(cpu), "family", def->family, &error_abort);
5255 object_property_set_int(OBJECT(cpu), "model", def->model, &error_abort);
5256 object_property_set_int(OBJECT(cpu), "stepping", def->stepping,
5257 &error_abort);
5258 object_property_set_str(OBJECT(cpu), "model-id", def->model_id,
5259 &error_abort);
5260 for (w = 0; w < FEATURE_WORDS; w++) {
5261 env->features[w] = def->features[w];
5264 /* legacy-cache defaults to 'off' if CPU model provides cache info */
5265 cpu->legacy_cache = !def->cache_info;
5267 /* Special cases not set in the X86CPUDefinition structs: */
5268 /* TODO: in-kernel irqchip for hvf */
5269 if (kvm_enabled()) {
5270 if (!kvm_irqchip_in_kernel()) {
5271 x86_cpu_change_kvm_default("x2apic", "off");
5272 } else if (kvm_irqchip_is_split() && kvm_enable_x2apic()) {
5273 x86_cpu_change_kvm_default("kvm-msi-ext-dest-id", "on");
5276 x86_cpu_apply_props(cpu, kvm_default_props);
5277 } else if (tcg_enabled()) {
5278 x86_cpu_apply_props(cpu, tcg_default_props);
5281 env->features[FEAT_1_ECX] |= CPUID_EXT_HYPERVISOR;
5283 /* sysenter isn't supported in compatibility mode on AMD,
5284 * syscall isn't supported in compatibility mode on Intel.
5285 * Normally we advertise the actual CPU vendor, but you can
5286 * override this using the 'vendor' property if you want to use
5287 * KVM's sysenter/syscall emulation in compatibility mode and
5288 * when doing cross vendor migration
5290 vendor = def->vendor;
5291 if (accel_uses_host_cpuid()) {
5292 uint32_t ebx = 0, ecx = 0, edx = 0;
5293 host_cpuid(0, 0, NULL, &ebx, &ecx, &edx);
5294 x86_cpu_vendor_words2str(host_vendor, ebx, edx, ecx);
5295 vendor = host_vendor;
5298 object_property_set_str(OBJECT(cpu), "vendor", vendor, &error_abort);
5300 x86_cpu_apply_version_props(cpu, model);
5303 * Properties in versioned CPU model are not user specified features.
5304 * We can simply clear env->user_features here since it will be filled later
5305 * in x86_cpu_expand_features() based on plus_features and minus_features.
5307 memset(&env->user_features, 0, sizeof(env->user_features));
5310 #ifndef CONFIG_USER_ONLY
5311 /* Return a QDict containing keys for all properties that can be included
5312 * in static expansion of CPU models. All properties set by x86_cpu_load_model()
5313 * must be included in the dictionary.
5315 static QDict *x86_cpu_static_props(void)
5317 FeatureWord w;
5318 int i;
5319 static const char *props[] = {
5320 "min-level",
5321 "min-xlevel",
5322 "family",
5323 "model",
5324 "stepping",
5325 "model-id",
5326 "vendor",
5327 "lmce",
5328 NULL,
5330 static QDict *d;
5332 if (d) {
5333 return d;
5336 d = qdict_new();
5337 for (i = 0; props[i]; i++) {
5338 qdict_put_null(d, props[i]);
5341 for (w = 0; w < FEATURE_WORDS; w++) {
5342 FeatureWordInfo *fi = &feature_word_info[w];
5343 int bit;
5344 for (bit = 0; bit < 64; bit++) {
5345 if (!fi->feat_names[bit]) {
5346 continue;
5348 qdict_put_null(d, fi->feat_names[bit]);
5352 return d;
5355 /* Add an entry to @props dict, with the value for property. */
5356 static void x86_cpu_expand_prop(X86CPU *cpu, QDict *props, const char *prop)
5358 QObject *value = object_property_get_qobject(OBJECT(cpu), prop,
5359 &error_abort);
5361 qdict_put_obj(props, prop, value);
5364 /* Convert CPU model data from X86CPU object to a property dictionary
5365 * that can recreate exactly the same CPU model.
5367 static void x86_cpu_to_dict(X86CPU *cpu, QDict *props)
5369 QDict *sprops = x86_cpu_static_props();
5370 const QDictEntry *e;
5372 for (e = qdict_first(sprops); e; e = qdict_next(sprops, e)) {
5373 const char *prop = qdict_entry_key(e);
5374 x86_cpu_expand_prop(cpu, props, prop);
5378 /* Convert CPU model data from X86CPU object to a property dictionary
5379 * that can recreate exactly the same CPU model, including every
5380 * writeable QOM property.
5382 static void x86_cpu_to_dict_full(X86CPU *cpu, QDict *props)
5384 ObjectPropertyIterator iter;
5385 ObjectProperty *prop;
5387 object_property_iter_init(&iter, OBJECT(cpu));
5388 while ((prop = object_property_iter_next(&iter))) {
5389 /* skip read-only or write-only properties */
5390 if (!prop->get || !prop->set) {
5391 continue;
5394 /* "hotplugged" is the only property that is configurable
5395 * on the command-line but will be set differently on CPUs
5396 * created using "-cpu ... -smp ..." and by CPUs created
5397 * on the fly by x86_cpu_from_model() for querying. Skip it.
5399 if (!strcmp(prop->name, "hotplugged")) {
5400 continue;
5402 x86_cpu_expand_prop(cpu, props, prop->name);
5406 static void object_apply_props(Object *obj, QDict *props, Error **errp)
5408 const QDictEntry *prop;
5410 for (prop = qdict_first(props); prop; prop = qdict_next(props, prop)) {
5411 if (!object_property_set_qobject(obj, qdict_entry_key(prop),
5412 qdict_entry_value(prop), errp)) {
5413 break;
5418 /* Create X86CPU object according to model+props specification */
5419 static X86CPU *x86_cpu_from_model(const char *model, QDict *props, Error **errp)
5421 X86CPU *xc = NULL;
5422 X86CPUClass *xcc;
5423 Error *err = NULL;
5425 xcc = X86_CPU_CLASS(cpu_class_by_name(TYPE_X86_CPU, model));
5426 if (xcc == NULL) {
5427 error_setg(&err, "CPU model '%s' not found", model);
5428 goto out;
5431 xc = X86_CPU(object_new_with_class(OBJECT_CLASS(xcc)));
5432 if (props) {
5433 object_apply_props(OBJECT(xc), props, &err);
5434 if (err) {
5435 goto out;
5439 x86_cpu_expand_features(xc, &err);
5440 if (err) {
5441 goto out;
5444 out:
5445 if (err) {
5446 error_propagate(errp, err);
5447 object_unref(OBJECT(xc));
5448 xc = NULL;
5450 return xc;
5453 CpuModelExpansionInfo *
5454 qmp_query_cpu_model_expansion(CpuModelExpansionType type,
5455 CpuModelInfo *model,
5456 Error **errp)
5458 X86CPU *xc = NULL;
5459 Error *err = NULL;
5460 CpuModelExpansionInfo *ret = g_new0(CpuModelExpansionInfo, 1);
5461 QDict *props = NULL;
5462 const char *base_name;
5464 xc = x86_cpu_from_model(model->name,
5465 model->has_props ?
5466 qobject_to(QDict, model->props) :
5467 NULL, &err);
5468 if (err) {
5469 goto out;
5472 props = qdict_new();
5473 ret->model = g_new0(CpuModelInfo, 1);
5474 ret->model->props = QOBJECT(props);
5475 ret->model->has_props = true;
5477 switch (type) {
5478 case CPU_MODEL_EXPANSION_TYPE_STATIC:
5479 /* Static expansion will be based on "base" only */
5480 base_name = "base";
5481 x86_cpu_to_dict(xc, props);
5482 break;
5483 case CPU_MODEL_EXPANSION_TYPE_FULL:
5484 /* As we don't return every single property, full expansion needs
5485 * to keep the original model name+props, and add extra
5486 * properties on top of that.
5488 base_name = model->name;
5489 x86_cpu_to_dict_full(xc, props);
5490 break;
5491 default:
5492 error_setg(&err, "Unsupported expansion type");
5493 goto out;
5496 x86_cpu_to_dict(xc, props);
5498 ret->model->name = g_strdup(base_name);
5500 out:
5501 object_unref(OBJECT(xc));
5502 if (err) {
5503 error_propagate(errp, err);
5504 qapi_free_CpuModelExpansionInfo(ret);
5505 ret = NULL;
5507 return ret;
5509 #endif /* !CONFIG_USER_ONLY */
5511 static gchar *x86_gdb_arch_name(CPUState *cs)
5513 #ifdef TARGET_X86_64
5514 return g_strdup("i386:x86-64");
5515 #else
5516 return g_strdup("i386");
5517 #endif
5520 static void x86_cpu_cpudef_class_init(ObjectClass *oc, void *data)
5522 X86CPUModel *model = data;
5523 X86CPUClass *xcc = X86_CPU_CLASS(oc);
5524 CPUClass *cc = CPU_CLASS(oc);
5526 xcc->model = model;
5527 xcc->migration_safe = true;
5528 cc->deprecation_note = model->cpudef->deprecation_note;
5531 static void x86_register_cpu_model_type(const char *name, X86CPUModel *model)
5533 g_autofree char *typename = x86_cpu_type_name(name);
5534 TypeInfo ti = {
5535 .name = typename,
5536 .parent = TYPE_X86_CPU,
5537 .class_init = x86_cpu_cpudef_class_init,
5538 .class_data = model,
5541 type_register(&ti);
5544 static void x86_register_cpudef_types(X86CPUDefinition *def)
5546 X86CPUModel *m;
5547 const X86CPUVersionDefinition *vdef;
5549 /* AMD aliases are handled at runtime based on CPUID vendor, so
5550 * they shouldn't be set on the CPU model table.
5552 assert(!(def->features[FEAT_8000_0001_EDX] & CPUID_EXT2_AMD_ALIASES));
5553 /* catch mistakes instead of silently truncating model_id when too long */
5554 assert(def->model_id && strlen(def->model_id) <= 48);
5556 /* Unversioned model: */
5557 m = g_new0(X86CPUModel, 1);
5558 m->cpudef = def;
5559 m->version = CPU_VERSION_AUTO;
5560 m->is_alias = true;
5561 x86_register_cpu_model_type(def->name, m);
5563 /* Versioned models: */
5565 for (vdef = x86_cpu_def_get_versions(def); vdef->version; vdef++) {
5566 X86CPUModel *m = g_new0(X86CPUModel, 1);
5567 g_autofree char *name =
5568 x86_cpu_versioned_model_name(def, vdef->version);
5569 m->cpudef = def;
5570 m->version = vdef->version;
5571 m->note = vdef->note;
5572 x86_register_cpu_model_type(name, m);
5574 if (vdef->alias) {
5575 X86CPUModel *am = g_new0(X86CPUModel, 1);
5576 am->cpudef = def;
5577 am->version = vdef->version;
5578 am->is_alias = true;
5579 x86_register_cpu_model_type(vdef->alias, am);
5585 #if !defined(CONFIG_USER_ONLY)
5587 void cpu_clear_apic_feature(CPUX86State *env)
5589 env->features[FEAT_1_EDX] &= ~CPUID_APIC;
5592 #endif /* !CONFIG_USER_ONLY */
5594 void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count,
5595 uint32_t *eax, uint32_t *ebx,
5596 uint32_t *ecx, uint32_t *edx)
5598 X86CPU *cpu = env_archcpu(env);
5599 CPUState *cs = env_cpu(env);
5600 uint32_t die_offset;
5601 uint32_t limit;
5602 uint32_t signature[3];
5603 X86CPUTopoInfo topo_info;
5605 topo_info.dies_per_pkg = env->nr_dies;
5606 topo_info.cores_per_die = cs->nr_cores;
5607 topo_info.threads_per_core = cs->nr_threads;
5609 /* Calculate & apply limits for different index ranges */
5610 if (index >= 0xC0000000) {
5611 limit = env->cpuid_xlevel2;
5612 } else if (index >= 0x80000000) {
5613 limit = env->cpuid_xlevel;
5614 } else if (index >= 0x40000000) {
5615 limit = 0x40000001;
5616 } else {
5617 limit = env->cpuid_level;
5620 if (index > limit) {
5621 /* Intel documentation states that invalid EAX input will
5622 * return the same information as EAX=cpuid_level
5623 * (Intel SDM Vol. 2A - Instruction Set Reference - CPUID)
5625 index = env->cpuid_level;
5628 switch(index) {
5629 case 0:
5630 *eax = env->cpuid_level;
5631 *ebx = env->cpuid_vendor1;
5632 *edx = env->cpuid_vendor2;
5633 *ecx = env->cpuid_vendor3;
5634 break;
5635 case 1:
5636 *eax = env->cpuid_version;
5637 *ebx = (cpu->apic_id << 24) |
5638 8 << 8; /* CLFLUSH size in quad words, Linux wants it. */
5639 *ecx = env->features[FEAT_1_ECX];
5640 if ((*ecx & CPUID_EXT_XSAVE) && (env->cr[4] & CR4_OSXSAVE_MASK)) {
5641 *ecx |= CPUID_EXT_OSXSAVE;
5643 *edx = env->features[FEAT_1_EDX];
5644 if (cs->nr_cores * cs->nr_threads > 1) {
5645 *ebx |= (cs->nr_cores * cs->nr_threads) << 16;
5646 *edx |= CPUID_HT;
5648 if (!cpu->enable_pmu) {
5649 *ecx &= ~CPUID_EXT_PDCM;
5651 break;
5652 case 2:
5653 /* cache info: needed for Pentium Pro compatibility */
5654 if (cpu->cache_info_passthrough) {
5655 host_cpuid(index, 0, eax, ebx, ecx, edx);
5656 break;
5658 *eax = 1; /* Number of CPUID[EAX=2] calls required */
5659 *ebx = 0;
5660 if (!cpu->enable_l3_cache) {
5661 *ecx = 0;
5662 } else {
5663 *ecx = cpuid2_cache_descriptor(env->cache_info_cpuid2.l3_cache);
5665 *edx = (cpuid2_cache_descriptor(env->cache_info_cpuid2.l1d_cache) << 16) |
5666 (cpuid2_cache_descriptor(env->cache_info_cpuid2.l1i_cache) << 8) |
5667 (cpuid2_cache_descriptor(env->cache_info_cpuid2.l2_cache));
5668 break;
5669 case 4:
5670 /* cache info: needed for Core compatibility */
5671 if (cpu->cache_info_passthrough) {
5672 host_cpuid(index, count, eax, ebx, ecx, edx);
5673 /* QEMU gives out its own APIC IDs, never pass down bits 31..26. */
5674 *eax &= ~0xFC000000;
5675 if ((*eax & 31) && cs->nr_cores > 1) {
5676 *eax |= (cs->nr_cores - 1) << 26;
5678 } else {
5679 *eax = 0;
5680 switch (count) {
5681 case 0: /* L1 dcache info */
5682 encode_cache_cpuid4(env->cache_info_cpuid4.l1d_cache,
5683 1, cs->nr_cores,
5684 eax, ebx, ecx, edx);
5685 break;
5686 case 1: /* L1 icache info */
5687 encode_cache_cpuid4(env->cache_info_cpuid4.l1i_cache,
5688 1, cs->nr_cores,
5689 eax, ebx, ecx, edx);
5690 break;
5691 case 2: /* L2 cache info */
5692 encode_cache_cpuid4(env->cache_info_cpuid4.l2_cache,
5693 cs->nr_threads, cs->nr_cores,
5694 eax, ebx, ecx, edx);
5695 break;
5696 case 3: /* L3 cache info */
5697 die_offset = apicid_die_offset(&topo_info);
5698 if (cpu->enable_l3_cache) {
5699 encode_cache_cpuid4(env->cache_info_cpuid4.l3_cache,
5700 (1 << die_offset), cs->nr_cores,
5701 eax, ebx, ecx, edx);
5702 break;
5704 /* fall through */
5705 default: /* end of info */
5706 *eax = *ebx = *ecx = *edx = 0;
5707 break;
5710 break;
5711 case 5:
5712 /* MONITOR/MWAIT Leaf */
5713 *eax = cpu->mwait.eax; /* Smallest monitor-line size in bytes */
5714 *ebx = cpu->mwait.ebx; /* Largest monitor-line size in bytes */
5715 *ecx = cpu->mwait.ecx; /* flags */
5716 *edx = cpu->mwait.edx; /* mwait substates */
5717 break;
5718 case 6:
5719 /* Thermal and Power Leaf */
5720 *eax = env->features[FEAT_6_EAX];
5721 *ebx = 0;
5722 *ecx = 0;
5723 *edx = 0;
5724 break;
5725 case 7:
5726 /* Structured Extended Feature Flags Enumeration Leaf */
5727 if (count == 0) {
5728 /* Maximum ECX value for sub-leaves */
5729 *eax = env->cpuid_level_func7;
5730 *ebx = env->features[FEAT_7_0_EBX]; /* Feature flags */
5731 *ecx = env->features[FEAT_7_0_ECX]; /* Feature flags */
5732 if ((*ecx & CPUID_7_0_ECX_PKU) && env->cr[4] & CR4_PKE_MASK) {
5733 *ecx |= CPUID_7_0_ECX_OSPKE;
5735 *edx = env->features[FEAT_7_0_EDX]; /* Feature flags */
5736 } else if (count == 1) {
5737 *eax = env->features[FEAT_7_1_EAX];
5738 *ebx = 0;
5739 *ecx = 0;
5740 *edx = 0;
5741 } else {
5742 *eax = 0;
5743 *ebx = 0;
5744 *ecx = 0;
5745 *edx = 0;
5747 break;
5748 case 9:
5749 /* Direct Cache Access Information Leaf */
5750 *eax = 0; /* Bits 0-31 in DCA_CAP MSR */
5751 *ebx = 0;
5752 *ecx = 0;
5753 *edx = 0;
5754 break;
5755 case 0xA:
5756 /* Architectural Performance Monitoring Leaf */
5757 if (kvm_enabled() && cpu->enable_pmu) {
5758 KVMState *s = cs->kvm_state;
5760 *eax = kvm_arch_get_supported_cpuid(s, 0xA, count, R_EAX);
5761 *ebx = kvm_arch_get_supported_cpuid(s, 0xA, count, R_EBX);
5762 *ecx = kvm_arch_get_supported_cpuid(s, 0xA, count, R_ECX);
5763 *edx = kvm_arch_get_supported_cpuid(s, 0xA, count, R_EDX);
5764 } else if (hvf_enabled() && cpu->enable_pmu) {
5765 *eax = hvf_get_supported_cpuid(0xA, count, R_EAX);
5766 *ebx = hvf_get_supported_cpuid(0xA, count, R_EBX);
5767 *ecx = hvf_get_supported_cpuid(0xA, count, R_ECX);
5768 *edx = hvf_get_supported_cpuid(0xA, count, R_EDX);
5769 } else {
5770 *eax = 0;
5771 *ebx = 0;
5772 *ecx = 0;
5773 *edx = 0;
5775 break;
5776 case 0xB:
5777 /* Extended Topology Enumeration Leaf */
5778 if (!cpu->enable_cpuid_0xb) {
5779 *eax = *ebx = *ecx = *edx = 0;
5780 break;
5783 *ecx = count & 0xff;
5784 *edx = cpu->apic_id;
5786 switch (count) {
5787 case 0:
5788 *eax = apicid_core_offset(&topo_info);
5789 *ebx = cs->nr_threads;
5790 *ecx |= CPUID_TOPOLOGY_LEVEL_SMT;
5791 break;
5792 case 1:
5793 *eax = apicid_pkg_offset(&topo_info);
5794 *ebx = cs->nr_cores * cs->nr_threads;
5795 *ecx |= CPUID_TOPOLOGY_LEVEL_CORE;
5796 break;
5797 default:
5798 *eax = 0;
5799 *ebx = 0;
5800 *ecx |= CPUID_TOPOLOGY_LEVEL_INVALID;
5803 assert(!(*eax & ~0x1f));
5804 *ebx &= 0xffff; /* The count doesn't need to be reliable. */
5805 break;
5806 case 0x1F:
5807 /* V2 Extended Topology Enumeration Leaf */
5808 if (env->nr_dies < 2) {
5809 *eax = *ebx = *ecx = *edx = 0;
5810 break;
5813 *ecx = count & 0xff;
5814 *edx = cpu->apic_id;
5815 switch (count) {
5816 case 0:
5817 *eax = apicid_core_offset(&topo_info);
5818 *ebx = cs->nr_threads;
5819 *ecx |= CPUID_TOPOLOGY_LEVEL_SMT;
5820 break;
5821 case 1:
5822 *eax = apicid_die_offset(&topo_info);
5823 *ebx = cs->nr_cores * cs->nr_threads;
5824 *ecx |= CPUID_TOPOLOGY_LEVEL_CORE;
5825 break;
5826 case 2:
5827 *eax = apicid_pkg_offset(&topo_info);
5828 *ebx = env->nr_dies * cs->nr_cores * cs->nr_threads;
5829 *ecx |= CPUID_TOPOLOGY_LEVEL_DIE;
5830 break;
5831 default:
5832 *eax = 0;
5833 *ebx = 0;
5834 *ecx |= CPUID_TOPOLOGY_LEVEL_INVALID;
5836 assert(!(*eax & ~0x1f));
5837 *ebx &= 0xffff; /* The count doesn't need to be reliable. */
5838 break;
5839 case 0xD: {
5840 /* Processor Extended State */
5841 *eax = 0;
5842 *ebx = 0;
5843 *ecx = 0;
5844 *edx = 0;
5845 if (!(env->features[FEAT_1_ECX] & CPUID_EXT_XSAVE)) {
5846 break;
5849 if (count == 0) {
5850 *ecx = xsave_area_size(x86_cpu_xsave_components(cpu));
5851 *eax = env->features[FEAT_XSAVE_COMP_LO];
5852 *edx = env->features[FEAT_XSAVE_COMP_HI];
5854 * The initial value of xcr0 and ebx == 0, On host without kvm
5855 * commit 412a3c41(e.g., CentOS 6), the ebx's value always == 0
5856 * even through guest update xcr0, this will crash some legacy guest
5857 * (e.g., CentOS 6), So set ebx == ecx to workaroud it.
5859 *ebx = kvm_enabled() ? *ecx : xsave_area_size(env->xcr0);
5860 } else if (count == 1) {
5861 *eax = env->features[FEAT_XSAVE];
5862 } else if (count < ARRAY_SIZE(x86_ext_save_areas)) {
5863 if ((x86_cpu_xsave_components(cpu) >> count) & 1) {
5864 const ExtSaveArea *esa = &x86_ext_save_areas[count];
5865 *eax = esa->size;
5866 *ebx = esa->offset;
5869 break;
5871 case 0x14: {
5872 /* Intel Processor Trace Enumeration */
5873 *eax = 0;
5874 *ebx = 0;
5875 *ecx = 0;
5876 *edx = 0;
5877 if (!(env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_INTEL_PT) ||
5878 !kvm_enabled()) {
5879 break;
5882 if (count == 0) {
5883 *eax = INTEL_PT_MAX_SUBLEAF;
5884 *ebx = INTEL_PT_MINIMAL_EBX;
5885 *ecx = INTEL_PT_MINIMAL_ECX;
5886 if (env->features[FEAT_14_0_ECX] & CPUID_14_0_ECX_LIP) {
5887 *ecx |= CPUID_14_0_ECX_LIP;
5889 } else if (count == 1) {
5890 *eax = INTEL_PT_MTC_BITMAP | INTEL_PT_ADDR_RANGES_NUM;
5891 *ebx = INTEL_PT_PSB_BITMAP | INTEL_PT_CYCLE_BITMAP;
5893 break;
5895 case 0x40000000:
5897 * CPUID code in kvm_arch_init_vcpu() ignores stuff
5898 * set here, but we restrict to TCG none the less.
5900 if (tcg_enabled() && cpu->expose_tcg) {
5901 memcpy(signature, "TCGTCGTCGTCG", 12);
5902 *eax = 0x40000001;
5903 *ebx = signature[0];
5904 *ecx = signature[1];
5905 *edx = signature[2];
5906 } else {
5907 *eax = 0;
5908 *ebx = 0;
5909 *ecx = 0;
5910 *edx = 0;
5912 break;
5913 case 0x40000001:
5914 *eax = 0;
5915 *ebx = 0;
5916 *ecx = 0;
5917 *edx = 0;
5918 break;
5919 case 0x80000000:
5920 *eax = env->cpuid_xlevel;
5921 *ebx = env->cpuid_vendor1;
5922 *edx = env->cpuid_vendor2;
5923 *ecx = env->cpuid_vendor3;
5924 break;
5925 case 0x80000001:
5926 *eax = env->cpuid_version;
5927 *ebx = 0;
5928 *ecx = env->features[FEAT_8000_0001_ECX];
5929 *edx = env->features[FEAT_8000_0001_EDX];
5931 /* The Linux kernel checks for the CMPLegacy bit and
5932 * discards multiple thread information if it is set.
5933 * So don't set it here for Intel to make Linux guests happy.
5935 if (cs->nr_cores * cs->nr_threads > 1) {
5936 if (env->cpuid_vendor1 != CPUID_VENDOR_INTEL_1 ||
5937 env->cpuid_vendor2 != CPUID_VENDOR_INTEL_2 ||
5938 env->cpuid_vendor3 != CPUID_VENDOR_INTEL_3) {
5939 *ecx |= 1 << 1; /* CmpLegacy bit */
5942 break;
5943 case 0x80000002:
5944 case 0x80000003:
5945 case 0x80000004:
5946 *eax = env->cpuid_model[(index - 0x80000002) * 4 + 0];
5947 *ebx = env->cpuid_model[(index - 0x80000002) * 4 + 1];
5948 *ecx = env->cpuid_model[(index - 0x80000002) * 4 + 2];
5949 *edx = env->cpuid_model[(index - 0x80000002) * 4 + 3];
5950 break;
5951 case 0x80000005:
5952 /* cache info (L1 cache) */
5953 if (cpu->cache_info_passthrough) {
5954 host_cpuid(index, 0, eax, ebx, ecx, edx);
5955 break;
5957 *eax = (L1_DTLB_2M_ASSOC << 24) | (L1_DTLB_2M_ENTRIES << 16) |
5958 (L1_ITLB_2M_ASSOC << 8) | (L1_ITLB_2M_ENTRIES);
5959 *ebx = (L1_DTLB_4K_ASSOC << 24) | (L1_DTLB_4K_ENTRIES << 16) |
5960 (L1_ITLB_4K_ASSOC << 8) | (L1_ITLB_4K_ENTRIES);
5961 *ecx = encode_cache_cpuid80000005(env->cache_info_amd.l1d_cache);
5962 *edx = encode_cache_cpuid80000005(env->cache_info_amd.l1i_cache);
5963 break;
5964 case 0x80000006:
5965 /* cache info (L2 cache) */
5966 if (cpu->cache_info_passthrough) {
5967 host_cpuid(index, 0, eax, ebx, ecx, edx);
5968 break;
5970 *eax = (AMD_ENC_ASSOC(L2_DTLB_2M_ASSOC) << 28) |
5971 (L2_DTLB_2M_ENTRIES << 16) |
5972 (AMD_ENC_ASSOC(L2_ITLB_2M_ASSOC) << 12) |
5973 (L2_ITLB_2M_ENTRIES);
5974 *ebx = (AMD_ENC_ASSOC(L2_DTLB_4K_ASSOC) << 28) |
5975 (L2_DTLB_4K_ENTRIES << 16) |
5976 (AMD_ENC_ASSOC(L2_ITLB_4K_ASSOC) << 12) |
5977 (L2_ITLB_4K_ENTRIES);
5978 encode_cache_cpuid80000006(env->cache_info_amd.l2_cache,
5979 cpu->enable_l3_cache ?
5980 env->cache_info_amd.l3_cache : NULL,
5981 ecx, edx);
5982 break;
5983 case 0x80000007:
5984 *eax = 0;
5985 *ebx = 0;
5986 *ecx = 0;
5987 *edx = env->features[FEAT_8000_0007_EDX];
5988 break;
5989 case 0x80000008:
5990 /* virtual & phys address size in low 2 bytes. */
5991 if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_LM) {
5992 /* 64 bit processor */
5993 *eax = cpu->phys_bits; /* configurable physical bits */
5994 if (env->features[FEAT_7_0_ECX] & CPUID_7_0_ECX_LA57) {
5995 *eax |= 0x00003900; /* 57 bits virtual */
5996 } else {
5997 *eax |= 0x00003000; /* 48 bits virtual */
5999 } else {
6000 *eax = cpu->phys_bits;
6002 *ebx = env->features[FEAT_8000_0008_EBX];
6003 if (cs->nr_cores * cs->nr_threads > 1) {
6005 * Bits 15:12 is "The number of bits in the initial
6006 * Core::X86::Apic::ApicId[ApicId] value that indicate
6007 * thread ID within a package".
6008 * Bits 7:0 is "The number of threads in the package is NC+1"
6010 *ecx = (apicid_pkg_offset(&topo_info) << 12) |
6011 ((cs->nr_cores * cs->nr_threads) - 1);
6012 } else {
6013 *ecx = 0;
6015 *edx = 0;
6016 break;
6017 case 0x8000000A:
6018 if (env->features[FEAT_8000_0001_ECX] & CPUID_EXT3_SVM) {
6019 *eax = 0x00000001; /* SVM Revision */
6020 *ebx = 0x00000010; /* nr of ASIDs */
6021 *ecx = 0;
6022 *edx = env->features[FEAT_SVM]; /* optional features */
6023 } else {
6024 *eax = 0;
6025 *ebx = 0;
6026 *ecx = 0;
6027 *edx = 0;
6029 break;
6030 case 0x8000001D:
6031 *eax = 0;
6032 if (cpu->cache_info_passthrough) {
6033 host_cpuid(index, count, eax, ebx, ecx, edx);
6034 break;
6036 switch (count) {
6037 case 0: /* L1 dcache info */
6038 encode_cache_cpuid8000001d(env->cache_info_amd.l1d_cache,
6039 &topo_info, eax, ebx, ecx, edx);
6040 break;
6041 case 1: /* L1 icache info */
6042 encode_cache_cpuid8000001d(env->cache_info_amd.l1i_cache,
6043 &topo_info, eax, ebx, ecx, edx);
6044 break;
6045 case 2: /* L2 cache info */
6046 encode_cache_cpuid8000001d(env->cache_info_amd.l2_cache,
6047 &topo_info, eax, ebx, ecx, edx);
6048 break;
6049 case 3: /* L3 cache info */
6050 encode_cache_cpuid8000001d(env->cache_info_amd.l3_cache,
6051 &topo_info, eax, ebx, ecx, edx);
6052 break;
6053 default: /* end of info */
6054 *eax = *ebx = *ecx = *edx = 0;
6055 break;
6057 break;
6058 case 0x8000001E:
6059 if (cpu->core_id <= 255) {
6060 encode_topo_cpuid8000001e(cpu, &topo_info, eax, ebx, ecx, edx);
6061 } else {
6062 *eax = 0;
6063 *ebx = 0;
6064 *ecx = 0;
6065 *edx = 0;
6067 break;
6068 case 0xC0000000:
6069 *eax = env->cpuid_xlevel2;
6070 *ebx = 0;
6071 *ecx = 0;
6072 *edx = 0;
6073 break;
6074 case 0xC0000001:
6075 /* Support for VIA CPU's CPUID instruction */
6076 *eax = env->cpuid_version;
6077 *ebx = 0;
6078 *ecx = 0;
6079 *edx = env->features[FEAT_C000_0001_EDX];
6080 break;
6081 case 0xC0000002:
6082 case 0xC0000003:
6083 case 0xC0000004:
6084 /* Reserved for the future, and now filled with zero */
6085 *eax = 0;
6086 *ebx = 0;
6087 *ecx = 0;
6088 *edx = 0;
6089 break;
6090 case 0x8000001F:
6091 *eax = sev_enabled() ? 0x2 : 0;
6092 *eax |= sev_es_enabled() ? 0x8 : 0;
6093 *ebx = sev_get_cbit_position();
6094 *ebx |= sev_get_reduced_phys_bits() << 6;
6095 *ecx = 0;
6096 *edx = 0;
6097 break;
6098 default:
6099 /* reserved values: zero */
6100 *eax = 0;
6101 *ebx = 0;
6102 *ecx = 0;
6103 *edx = 0;
6104 break;
6108 static void x86_cpu_reset(DeviceState *dev)
6110 CPUState *s = CPU(dev);
6111 X86CPU *cpu = X86_CPU(s);
6112 X86CPUClass *xcc = X86_CPU_GET_CLASS(cpu);
6113 CPUX86State *env = &cpu->env;
6114 target_ulong cr4;
6115 uint64_t xcr0;
6116 int i;
6118 xcc->parent_reset(dev);
6120 memset(env, 0, offsetof(CPUX86State, end_reset_fields));
6122 env->old_exception = -1;
6124 /* init to reset state */
6126 env->hflags2 |= HF2_GIF_MASK;
6127 env->hflags &= ~HF_GUEST_MASK;
6129 cpu_x86_update_cr0(env, 0x60000010);
6130 env->a20_mask = ~0x0;
6131 env->smbase = 0x30000;
6132 env->msr_smi_count = 0;
6134 env->idt.limit = 0xffff;
6135 env->gdt.limit = 0xffff;
6136 env->ldt.limit = 0xffff;
6137 env->ldt.flags = DESC_P_MASK | (2 << DESC_TYPE_SHIFT);
6138 env->tr.limit = 0xffff;
6139 env->tr.flags = DESC_P_MASK | (11 << DESC_TYPE_SHIFT);
6141 cpu_x86_load_seg_cache(env, R_CS, 0xf000, 0xffff0000, 0xffff,
6142 DESC_P_MASK | DESC_S_MASK | DESC_CS_MASK |
6143 DESC_R_MASK | DESC_A_MASK);
6144 cpu_x86_load_seg_cache(env, R_DS, 0, 0, 0xffff,
6145 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
6146 DESC_A_MASK);
6147 cpu_x86_load_seg_cache(env, R_ES, 0, 0, 0xffff,
6148 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
6149 DESC_A_MASK);
6150 cpu_x86_load_seg_cache(env, R_SS, 0, 0, 0xffff,
6151 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
6152 DESC_A_MASK);
6153 cpu_x86_load_seg_cache(env, R_FS, 0, 0, 0xffff,
6154 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
6155 DESC_A_MASK);
6156 cpu_x86_load_seg_cache(env, R_GS, 0, 0, 0xffff,
6157 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
6158 DESC_A_MASK);
6160 env->eip = 0xfff0;
6161 env->regs[R_EDX] = env->cpuid_version;
6163 env->eflags = 0x2;
6165 /* FPU init */
6166 for (i = 0; i < 8; i++) {
6167 env->fptags[i] = 1;
6169 cpu_set_fpuc(env, 0x37f);
6171 env->mxcsr = 0x1f80;
6172 /* All units are in INIT state. */
6173 env->xstate_bv = 0;
6175 env->pat = 0x0007040600070406ULL;
6176 env->msr_ia32_misc_enable = MSR_IA32_MISC_ENABLE_DEFAULT;
6177 if (env->features[FEAT_1_ECX] & CPUID_EXT_MONITOR) {
6178 env->msr_ia32_misc_enable |= MSR_IA32_MISC_ENABLE_MWAIT;
6181 memset(env->dr, 0, sizeof(env->dr));
6182 env->dr[6] = DR6_FIXED_1;
6183 env->dr[7] = DR7_FIXED_1;
6184 cpu_breakpoint_remove_all(s, BP_CPU);
6185 cpu_watchpoint_remove_all(s, BP_CPU);
6187 cr4 = 0;
6188 xcr0 = XSTATE_FP_MASK;
6190 #ifdef CONFIG_USER_ONLY
6191 /* Enable all the features for user-mode. */
6192 if (env->features[FEAT_1_EDX] & CPUID_SSE) {
6193 xcr0 |= XSTATE_SSE_MASK;
6195 for (i = 2; i < ARRAY_SIZE(x86_ext_save_areas); i++) {
6196 const ExtSaveArea *esa = &x86_ext_save_areas[i];
6197 if (env->features[esa->feature] & esa->bits) {
6198 xcr0 |= 1ull << i;
6202 if (env->features[FEAT_1_ECX] & CPUID_EXT_XSAVE) {
6203 cr4 |= CR4_OSFXSR_MASK | CR4_OSXSAVE_MASK;
6205 if (env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_FSGSBASE) {
6206 cr4 |= CR4_FSGSBASE_MASK;
6208 #endif
6210 env->xcr0 = xcr0;
6211 cpu_x86_update_cr4(env, cr4);
6214 * SDM 11.11.5 requires:
6215 * - IA32_MTRR_DEF_TYPE MSR.E = 0
6216 * - IA32_MTRR_PHYSMASKn.V = 0
6217 * All other bits are undefined. For simplification, zero it all.
6219 env->mtrr_deftype = 0;
6220 memset(env->mtrr_var, 0, sizeof(env->mtrr_var));
6221 memset(env->mtrr_fixed, 0, sizeof(env->mtrr_fixed));
6223 env->interrupt_injected = -1;
6224 env->exception_nr = -1;
6225 env->exception_pending = 0;
6226 env->exception_injected = 0;
6227 env->exception_has_payload = false;
6228 env->exception_payload = 0;
6229 env->nmi_injected = false;
6230 #if !defined(CONFIG_USER_ONLY)
6231 /* We hard-wire the BSP to the first CPU. */
6232 apic_designate_bsp(cpu->apic_state, s->cpu_index == 0);
6234 s->halted = !cpu_is_bsp(cpu);
6236 if (kvm_enabled()) {
6237 kvm_arch_reset_vcpu(cpu);
6239 #endif
6242 #ifndef CONFIG_USER_ONLY
6243 bool cpu_is_bsp(X86CPU *cpu)
6245 return cpu_get_apic_base(cpu->apic_state) & MSR_IA32_APICBASE_BSP;
6248 /* TODO: remove me, when reset over QOM tree is implemented */
6249 static void x86_cpu_machine_reset_cb(void *opaque)
6251 X86CPU *cpu = opaque;
6252 cpu_reset(CPU(cpu));
6254 #endif
6256 static void mce_init(X86CPU *cpu)
6258 CPUX86State *cenv = &cpu->env;
6259 unsigned int bank;
6261 if (((cenv->cpuid_version >> 8) & 0xf) >= 6
6262 && (cenv->features[FEAT_1_EDX] & (CPUID_MCE | CPUID_MCA)) ==
6263 (CPUID_MCE | CPUID_MCA)) {
6264 cenv->mcg_cap = MCE_CAP_DEF | MCE_BANKS_DEF |
6265 (cpu->enable_lmce ? MCG_LMCE_P : 0);
6266 cenv->mcg_ctl = ~(uint64_t)0;
6267 for (bank = 0; bank < MCE_BANKS_DEF; bank++) {
6268 cenv->mce_banks[bank * 4] = ~(uint64_t)0;
6273 #ifndef CONFIG_USER_ONLY
6274 APICCommonClass *apic_get_class(void)
6276 const char *apic_type = "apic";
6278 /* TODO: in-kernel irqchip for hvf */
6279 if (kvm_apic_in_kernel()) {
6280 apic_type = "kvm-apic";
6281 } else if (xen_enabled()) {
6282 apic_type = "xen-apic";
6283 } else if (whpx_apic_in_platform()) {
6284 apic_type = "whpx-apic";
6287 return APIC_COMMON_CLASS(object_class_by_name(apic_type));
6290 static void x86_cpu_apic_create(X86CPU *cpu, Error **errp)
6292 APICCommonState *apic;
6293 ObjectClass *apic_class = OBJECT_CLASS(apic_get_class());
6295 cpu->apic_state = DEVICE(object_new_with_class(apic_class));
6297 object_property_add_child(OBJECT(cpu), "lapic",
6298 OBJECT(cpu->apic_state));
6299 object_unref(OBJECT(cpu->apic_state));
6301 qdev_prop_set_uint32(cpu->apic_state, "id", cpu->apic_id);
6302 /* TODO: convert to link<> */
6303 apic = APIC_COMMON(cpu->apic_state);
6304 apic->cpu = cpu;
6305 apic->apicbase = APIC_DEFAULT_ADDRESS | MSR_IA32_APICBASE_ENABLE;
6308 static void x86_cpu_apic_realize(X86CPU *cpu, Error **errp)
6310 APICCommonState *apic;
6311 static bool apic_mmio_map_once;
6313 if (cpu->apic_state == NULL) {
6314 return;
6316 qdev_realize(DEVICE(cpu->apic_state), NULL, errp);
6318 /* Map APIC MMIO area */
6319 apic = APIC_COMMON(cpu->apic_state);
6320 if (!apic_mmio_map_once) {
6321 memory_region_add_subregion_overlap(get_system_memory(),
6322 apic->apicbase &
6323 MSR_IA32_APICBASE_BASE,
6324 &apic->io_memory,
6325 0x1000);
6326 apic_mmio_map_once = true;
6330 static void x86_cpu_machine_done(Notifier *n, void *unused)
6332 X86CPU *cpu = container_of(n, X86CPU, machine_done);
6333 MemoryRegion *smram =
6334 (MemoryRegion *) object_resolve_path("/machine/smram", NULL);
6336 if (smram) {
6337 cpu->smram = g_new(MemoryRegion, 1);
6338 memory_region_init_alias(cpu->smram, OBJECT(cpu), "smram",
6339 smram, 0, 4 * GiB);
6340 memory_region_set_enabled(cpu->smram, true);
6341 memory_region_add_subregion_overlap(cpu->cpu_as_root, 0, cpu->smram, 1);
6344 #else
6345 static void x86_cpu_apic_realize(X86CPU *cpu, Error **errp)
6348 #endif
6350 /* Note: Only safe for use on x86(-64) hosts */
6351 static uint32_t x86_host_phys_bits(void)
6353 uint32_t eax;
6354 uint32_t host_phys_bits;
6356 host_cpuid(0x80000000, 0, &eax, NULL, NULL, NULL);
6357 if (eax >= 0x80000008) {
6358 host_cpuid(0x80000008, 0, &eax, NULL, NULL, NULL);
6359 /* Note: According to AMD doc 25481 rev 2.34 they have a field
6360 * at 23:16 that can specify a maximum physical address bits for
6361 * the guest that can override this value; but I've not seen
6362 * anything with that set.
6364 host_phys_bits = eax & 0xff;
6365 } else {
6366 /* It's an odd 64 bit machine that doesn't have the leaf for
6367 * physical address bits; fall back to 36 that's most older
6368 * Intel.
6370 host_phys_bits = 36;
6373 return host_phys_bits;
6376 static void x86_cpu_adjust_level(X86CPU *cpu, uint32_t *min, uint32_t value)
6378 if (*min < value) {
6379 *min = value;
6383 /* Increase cpuid_min_{level,xlevel,xlevel2} automatically, if appropriate */
6384 static void x86_cpu_adjust_feat_level(X86CPU *cpu, FeatureWord w)
6386 CPUX86State *env = &cpu->env;
6387 FeatureWordInfo *fi = &feature_word_info[w];
6388 uint32_t eax = fi->cpuid.eax;
6389 uint32_t region = eax & 0xF0000000;
6391 assert(feature_word_info[w].type == CPUID_FEATURE_WORD);
6392 if (!env->features[w]) {
6393 return;
6396 switch (region) {
6397 case 0x00000000:
6398 x86_cpu_adjust_level(cpu, &env->cpuid_min_level, eax);
6399 break;
6400 case 0x80000000:
6401 x86_cpu_adjust_level(cpu, &env->cpuid_min_xlevel, eax);
6402 break;
6403 case 0xC0000000:
6404 x86_cpu_adjust_level(cpu, &env->cpuid_min_xlevel2, eax);
6405 break;
6408 if (eax == 7) {
6409 x86_cpu_adjust_level(cpu, &env->cpuid_min_level_func7,
6410 fi->cpuid.ecx);
6414 /* Calculate XSAVE components based on the configured CPU feature flags */
6415 static void x86_cpu_enable_xsave_components(X86CPU *cpu)
6417 CPUX86State *env = &cpu->env;
6418 int i;
6419 uint64_t mask;
6421 if (!(env->features[FEAT_1_ECX] & CPUID_EXT_XSAVE)) {
6422 env->features[FEAT_XSAVE_COMP_LO] = 0;
6423 env->features[FEAT_XSAVE_COMP_HI] = 0;
6424 return;
6427 mask = 0;
6428 for (i = 0; i < ARRAY_SIZE(x86_ext_save_areas); i++) {
6429 const ExtSaveArea *esa = &x86_ext_save_areas[i];
6430 if (env->features[esa->feature] & esa->bits) {
6431 mask |= (1ULL << i);
6435 env->features[FEAT_XSAVE_COMP_LO] = mask;
6436 env->features[FEAT_XSAVE_COMP_HI] = mask >> 32;
6439 /***** Steps involved on loading and filtering CPUID data
6441 * When initializing and realizing a CPU object, the steps
6442 * involved in setting up CPUID data are:
6444 * 1) Loading CPU model definition (X86CPUDefinition). This is
6445 * implemented by x86_cpu_load_model() and should be completely
6446 * transparent, as it is done automatically by instance_init.
6447 * No code should need to look at X86CPUDefinition structs
6448 * outside instance_init.
6450 * 2) CPU expansion. This is done by realize before CPUID
6451 * filtering, and will make sure host/accelerator data is
6452 * loaded for CPU models that depend on host capabilities
6453 * (e.g. "host"). Done by x86_cpu_expand_features().
6455 * 3) CPUID filtering. This initializes extra data related to
6456 * CPUID, and checks if the host supports all capabilities
6457 * required by the CPU. Runnability of a CPU model is
6458 * determined at this step. Done by x86_cpu_filter_features().
6460 * Some operations don't require all steps to be performed.
6461 * More precisely:
6463 * - CPU instance creation (instance_init) will run only CPU
6464 * model loading. CPU expansion can't run at instance_init-time
6465 * because host/accelerator data may be not available yet.
6466 * - CPU realization will perform both CPU model expansion and CPUID
6467 * filtering, and return an error in case one of them fails.
6468 * - query-cpu-definitions needs to run all 3 steps. It needs
6469 * to run CPUID filtering, as the 'unavailable-features'
6470 * field is set based on the filtering results.
6471 * - The query-cpu-model-expansion QMP command only needs to run
6472 * CPU model loading and CPU expansion. It should not filter
6473 * any CPUID data based on host capabilities.
6476 /* Expand CPU configuration data, based on configured features
6477 * and host/accelerator capabilities when appropriate.
6479 static void x86_cpu_expand_features(X86CPU *cpu, Error **errp)
6481 CPUX86State *env = &cpu->env;
6482 FeatureWord w;
6483 int i;
6484 GList *l;
6486 for (l = plus_features; l; l = l->next) {
6487 const char *prop = l->data;
6488 if (!object_property_set_bool(OBJECT(cpu), prop, true, errp)) {
6489 return;
6493 for (l = minus_features; l; l = l->next) {
6494 const char *prop = l->data;
6495 if (!object_property_set_bool(OBJECT(cpu), prop, false, errp)) {
6496 return;
6500 /*TODO: Now cpu->max_features doesn't overwrite features
6501 * set using QOM properties, and we can convert
6502 * plus_features & minus_features to global properties
6503 * inside x86_cpu_parse_featurestr() too.
6505 if (cpu->max_features) {
6506 for (w = 0; w < FEATURE_WORDS; w++) {
6507 /* Override only features that weren't set explicitly
6508 * by the user.
6510 env->features[w] |=
6511 x86_cpu_get_supported_feature_word(w, cpu->migratable) &
6512 ~env->user_features[w] &
6513 ~feature_word_info[w].no_autoenable_flags;
6517 for (i = 0; i < ARRAY_SIZE(feature_dependencies); i++) {
6518 FeatureDep *d = &feature_dependencies[i];
6519 if (!(env->features[d->from.index] & d->from.mask)) {
6520 uint64_t unavailable_features = env->features[d->to.index] & d->to.mask;
6522 /* Not an error unless the dependent feature was added explicitly. */
6523 mark_unavailable_features(cpu, d->to.index,
6524 unavailable_features & env->user_features[d->to.index],
6525 "This feature depends on other features that were not requested");
6527 env->features[d->to.index] &= ~unavailable_features;
6531 if (!kvm_enabled() || !cpu->expose_kvm) {
6532 env->features[FEAT_KVM] = 0;
6535 x86_cpu_enable_xsave_components(cpu);
6537 /* CPUID[EAX=7,ECX=0].EBX always increased level automatically: */
6538 x86_cpu_adjust_feat_level(cpu, FEAT_7_0_EBX);
6539 if (cpu->full_cpuid_auto_level) {
6540 x86_cpu_adjust_feat_level(cpu, FEAT_1_EDX);
6541 x86_cpu_adjust_feat_level(cpu, FEAT_1_ECX);
6542 x86_cpu_adjust_feat_level(cpu, FEAT_6_EAX);
6543 x86_cpu_adjust_feat_level(cpu, FEAT_7_0_ECX);
6544 x86_cpu_adjust_feat_level(cpu, FEAT_7_1_EAX);
6545 x86_cpu_adjust_feat_level(cpu, FEAT_8000_0001_EDX);
6546 x86_cpu_adjust_feat_level(cpu, FEAT_8000_0001_ECX);
6547 x86_cpu_adjust_feat_level(cpu, FEAT_8000_0007_EDX);
6548 x86_cpu_adjust_feat_level(cpu, FEAT_8000_0008_EBX);
6549 x86_cpu_adjust_feat_level(cpu, FEAT_C000_0001_EDX);
6550 x86_cpu_adjust_feat_level(cpu, FEAT_SVM);
6551 x86_cpu_adjust_feat_level(cpu, FEAT_XSAVE);
6553 /* Intel Processor Trace requires CPUID[0x14] */
6554 if ((env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_INTEL_PT)) {
6555 if (cpu->intel_pt_auto_level) {
6556 x86_cpu_adjust_level(cpu, &cpu->env.cpuid_min_level, 0x14);
6557 } else if (cpu->env.cpuid_min_level < 0x14) {
6558 mark_unavailable_features(cpu, FEAT_7_0_EBX,
6559 CPUID_7_0_EBX_INTEL_PT,
6560 "Intel PT need CPUID leaf 0x14, please set by \"-cpu ...,intel-pt=on,min-level=0x14\"");
6564 /* CPU topology with multi-dies support requires CPUID[0x1F] */
6565 if (env->nr_dies > 1) {
6566 x86_cpu_adjust_level(cpu, &env->cpuid_min_level, 0x1F);
6569 /* SVM requires CPUID[0x8000000A] */
6570 if (env->features[FEAT_8000_0001_ECX] & CPUID_EXT3_SVM) {
6571 x86_cpu_adjust_level(cpu, &env->cpuid_min_xlevel, 0x8000000A);
6574 /* SEV requires CPUID[0x8000001F] */
6575 if (sev_enabled()) {
6576 x86_cpu_adjust_level(cpu, &env->cpuid_min_xlevel, 0x8000001F);
6580 /* Set cpuid_*level* based on cpuid_min_*level, if not explicitly set */
6581 if (env->cpuid_level_func7 == UINT32_MAX) {
6582 env->cpuid_level_func7 = env->cpuid_min_level_func7;
6584 if (env->cpuid_level == UINT32_MAX) {
6585 env->cpuid_level = env->cpuid_min_level;
6587 if (env->cpuid_xlevel == UINT32_MAX) {
6588 env->cpuid_xlevel = env->cpuid_min_xlevel;
6590 if (env->cpuid_xlevel2 == UINT32_MAX) {
6591 env->cpuid_xlevel2 = env->cpuid_min_xlevel2;
6596 * Finishes initialization of CPUID data, filters CPU feature
6597 * words based on host availability of each feature.
6599 * Returns: 0 if all flags are supported by the host, non-zero otherwise.
6601 static void x86_cpu_filter_features(X86CPU *cpu, bool verbose)
6603 CPUX86State *env = &cpu->env;
6604 FeatureWord w;
6605 const char *prefix = NULL;
6607 if (verbose) {
6608 prefix = accel_uses_host_cpuid()
6609 ? "host doesn't support requested feature"
6610 : "TCG doesn't support requested feature";
6613 for (w = 0; w < FEATURE_WORDS; w++) {
6614 uint64_t host_feat =
6615 x86_cpu_get_supported_feature_word(w, false);
6616 uint64_t requested_features = env->features[w];
6617 uint64_t unavailable_features = requested_features & ~host_feat;
6618 mark_unavailable_features(cpu, w, unavailable_features, prefix);
6621 if ((env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_INTEL_PT) &&
6622 kvm_enabled()) {
6623 KVMState *s = CPU(cpu)->kvm_state;
6624 uint32_t eax_0 = kvm_arch_get_supported_cpuid(s, 0x14, 0, R_EAX);
6625 uint32_t ebx_0 = kvm_arch_get_supported_cpuid(s, 0x14, 0, R_EBX);
6626 uint32_t ecx_0 = kvm_arch_get_supported_cpuid(s, 0x14, 0, R_ECX);
6627 uint32_t eax_1 = kvm_arch_get_supported_cpuid(s, 0x14, 1, R_EAX);
6628 uint32_t ebx_1 = kvm_arch_get_supported_cpuid(s, 0x14, 1, R_EBX);
6630 if (!eax_0 ||
6631 ((ebx_0 & INTEL_PT_MINIMAL_EBX) != INTEL_PT_MINIMAL_EBX) ||
6632 ((ecx_0 & INTEL_PT_MINIMAL_ECX) != INTEL_PT_MINIMAL_ECX) ||
6633 ((eax_1 & INTEL_PT_MTC_BITMAP) != INTEL_PT_MTC_BITMAP) ||
6634 ((eax_1 & INTEL_PT_ADDR_RANGES_NUM_MASK) <
6635 INTEL_PT_ADDR_RANGES_NUM) ||
6636 ((ebx_1 & (INTEL_PT_PSB_BITMAP | INTEL_PT_CYCLE_BITMAP)) !=
6637 (INTEL_PT_PSB_BITMAP | INTEL_PT_CYCLE_BITMAP)) ||
6638 ((ecx_0 & CPUID_14_0_ECX_LIP) !=
6639 (env->features[FEAT_14_0_ECX] & CPUID_14_0_ECX_LIP))) {
6641 * Processor Trace capabilities aren't configurable, so if the
6642 * host can't emulate the capabilities we report on
6643 * cpu_x86_cpuid(), intel-pt can't be enabled on the current host.
6645 mark_unavailable_features(cpu, FEAT_7_0_EBX, CPUID_7_0_EBX_INTEL_PT, prefix);
6650 static void x86_cpu_hyperv_realize(X86CPU *cpu)
6652 size_t len;
6654 /* Hyper-V vendor id */
6655 if (!cpu->hyperv_vendor) {
6656 memcpy(cpu->hyperv_vendor_id, "Microsoft Hv", 12);
6657 } else {
6658 len = strlen(cpu->hyperv_vendor);
6660 if (len > 12) {
6661 warn_report("hv-vendor-id truncated to 12 characters");
6662 len = 12;
6664 memset(cpu->hyperv_vendor_id, 0, 12);
6665 memcpy(cpu->hyperv_vendor_id, cpu->hyperv_vendor, len);
6668 /* 'Hv#1' interface identification*/
6669 cpu->hyperv_interface_id[0] = 0x31237648;
6670 cpu->hyperv_interface_id[1] = 0;
6671 cpu->hyperv_interface_id[2] = 0;
6672 cpu->hyperv_interface_id[3] = 0;
6674 /* Hypervisor system identity */
6675 cpu->hyperv_version_id[0] = 0x00001bbc;
6676 cpu->hyperv_version_id[1] = 0x00060001;
6678 /* Hypervisor implementation limits */
6679 cpu->hyperv_limits[0] = 64;
6680 cpu->hyperv_limits[1] = 0;
6681 cpu->hyperv_limits[2] = 0;
6684 static void x86_cpu_realizefn(DeviceState *dev, Error **errp)
6686 CPUState *cs = CPU(dev);
6687 X86CPU *cpu = X86_CPU(dev);
6688 X86CPUClass *xcc = X86_CPU_GET_CLASS(dev);
6689 CPUX86State *env = &cpu->env;
6690 Error *local_err = NULL;
6691 static bool ht_warned;
6693 if (xcc->host_cpuid_required) {
6694 if (!accel_uses_host_cpuid()) {
6695 g_autofree char *name = x86_cpu_class_get_model_name(xcc);
6696 error_setg(&local_err, "CPU model '%s' requires KVM", name);
6697 goto out;
6701 if (cpu->max_features && accel_uses_host_cpuid()) {
6702 if (enable_cpu_pm) {
6703 host_cpuid(5, 0, &cpu->mwait.eax, &cpu->mwait.ebx,
6704 &cpu->mwait.ecx, &cpu->mwait.edx);
6705 env->features[FEAT_1_ECX] |= CPUID_EXT_MONITOR;
6706 if (kvm_enabled() && kvm_has_waitpkg()) {
6707 env->features[FEAT_7_0_ECX] |= CPUID_7_0_ECX_WAITPKG;
6710 if (kvm_enabled() && cpu->ucode_rev == 0) {
6711 cpu->ucode_rev = kvm_arch_get_supported_msr_feature(kvm_state,
6712 MSR_IA32_UCODE_REV);
6716 if (cpu->ucode_rev == 0) {
6717 /* The default is the same as KVM's. */
6718 if (IS_AMD_CPU(env)) {
6719 cpu->ucode_rev = 0x01000065;
6720 } else {
6721 cpu->ucode_rev = 0x100000000ULL;
6725 /* mwait extended info: needed for Core compatibility */
6726 /* We always wake on interrupt even if host does not have the capability */
6727 cpu->mwait.ecx |= CPUID_MWAIT_EMX | CPUID_MWAIT_IBE;
6729 if (cpu->apic_id == UNASSIGNED_APIC_ID) {
6730 error_setg(errp, "apic-id property was not initialized properly");
6731 return;
6734 x86_cpu_expand_features(cpu, &local_err);
6735 if (local_err) {
6736 goto out;
6739 x86_cpu_filter_features(cpu, cpu->check_cpuid || cpu->enforce_cpuid);
6741 if (cpu->enforce_cpuid && x86_cpu_have_filtered_features(cpu)) {
6742 error_setg(&local_err,
6743 accel_uses_host_cpuid() ?
6744 "Host doesn't support requested features" :
6745 "TCG doesn't support requested features");
6746 goto out;
6749 /* On AMD CPUs, some CPUID[8000_0001].EDX bits must match the bits on
6750 * CPUID[1].EDX.
6752 if (IS_AMD_CPU(env)) {
6753 env->features[FEAT_8000_0001_EDX] &= ~CPUID_EXT2_AMD_ALIASES;
6754 env->features[FEAT_8000_0001_EDX] |= (env->features[FEAT_1_EDX]
6755 & CPUID_EXT2_AMD_ALIASES);
6758 /* For 64bit systems think about the number of physical bits to present.
6759 * ideally this should be the same as the host; anything other than matching
6760 * the host can cause incorrect guest behaviour.
6761 * QEMU used to pick the magic value of 40 bits that corresponds to
6762 * consumer AMD devices but nothing else.
6764 if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_LM) {
6765 if (accel_uses_host_cpuid()) {
6766 uint32_t host_phys_bits = x86_host_phys_bits();
6767 static bool warned;
6769 /* Print a warning if the user set it to a value that's not the
6770 * host value.
6772 if (cpu->phys_bits != host_phys_bits && cpu->phys_bits != 0 &&
6773 !warned) {
6774 warn_report("Host physical bits (%u)"
6775 " does not match phys-bits property (%u)",
6776 host_phys_bits, cpu->phys_bits);
6777 warned = true;
6780 if (cpu->host_phys_bits) {
6781 /* The user asked for us to use the host physical bits */
6782 cpu->phys_bits = host_phys_bits;
6783 if (cpu->host_phys_bits_limit &&
6784 cpu->phys_bits > cpu->host_phys_bits_limit) {
6785 cpu->phys_bits = cpu->host_phys_bits_limit;
6789 if (cpu->phys_bits &&
6790 (cpu->phys_bits > TARGET_PHYS_ADDR_SPACE_BITS ||
6791 cpu->phys_bits < 32)) {
6792 error_setg(errp, "phys-bits should be between 32 and %u "
6793 " (but is %u)",
6794 TARGET_PHYS_ADDR_SPACE_BITS, cpu->phys_bits);
6795 return;
6797 } else {
6798 if (cpu->phys_bits && cpu->phys_bits != TCG_PHYS_ADDR_BITS) {
6799 error_setg(errp, "TCG only supports phys-bits=%u",
6800 TCG_PHYS_ADDR_BITS);
6801 return;
6804 /* 0 means it was not explicitly set by the user (or by machine
6805 * compat_props or by the host code above). In this case, the default
6806 * is the value used by TCG (40).
6808 if (cpu->phys_bits == 0) {
6809 cpu->phys_bits = TCG_PHYS_ADDR_BITS;
6811 } else {
6812 /* For 32 bit systems don't use the user set value, but keep
6813 * phys_bits consistent with what we tell the guest.
6815 if (cpu->phys_bits != 0) {
6816 error_setg(errp, "phys-bits is not user-configurable in 32 bit");
6817 return;
6820 if (env->features[FEAT_1_EDX] & CPUID_PSE36) {
6821 cpu->phys_bits = 36;
6822 } else {
6823 cpu->phys_bits = 32;
6827 /* Cache information initialization */
6828 if (!cpu->legacy_cache) {
6829 if (!xcc->model || !xcc->model->cpudef->cache_info) {
6830 g_autofree char *name = x86_cpu_class_get_model_name(xcc);
6831 error_setg(errp,
6832 "CPU model '%s' doesn't support legacy-cache=off", name);
6833 return;
6835 env->cache_info_cpuid2 = env->cache_info_cpuid4 = env->cache_info_amd =
6836 *xcc->model->cpudef->cache_info;
6837 } else {
6838 /* Build legacy cache information */
6839 env->cache_info_cpuid2.l1d_cache = &legacy_l1d_cache;
6840 env->cache_info_cpuid2.l1i_cache = &legacy_l1i_cache;
6841 env->cache_info_cpuid2.l2_cache = &legacy_l2_cache_cpuid2;
6842 env->cache_info_cpuid2.l3_cache = &legacy_l3_cache;
6844 env->cache_info_cpuid4.l1d_cache = &legacy_l1d_cache;
6845 env->cache_info_cpuid4.l1i_cache = &legacy_l1i_cache;
6846 env->cache_info_cpuid4.l2_cache = &legacy_l2_cache;
6847 env->cache_info_cpuid4.l3_cache = &legacy_l3_cache;
6849 env->cache_info_amd.l1d_cache = &legacy_l1d_cache_amd;
6850 env->cache_info_amd.l1i_cache = &legacy_l1i_cache_amd;
6851 env->cache_info_amd.l2_cache = &legacy_l2_cache_amd;
6852 env->cache_info_amd.l3_cache = &legacy_l3_cache;
6855 /* Process Hyper-V enlightenments */
6856 x86_cpu_hyperv_realize(cpu);
6858 cpu_exec_realizefn(cs, &local_err);
6859 if (local_err != NULL) {
6860 error_propagate(errp, local_err);
6861 return;
6864 #ifndef CONFIG_USER_ONLY
6865 MachineState *ms = MACHINE(qdev_get_machine());
6866 qemu_register_reset(x86_cpu_machine_reset_cb, cpu);
6868 if (cpu->env.features[FEAT_1_EDX] & CPUID_APIC || ms->smp.cpus > 1) {
6869 x86_cpu_apic_create(cpu, &local_err);
6870 if (local_err != NULL) {
6871 goto out;
6874 #endif
6876 mce_init(cpu);
6878 #ifndef CONFIG_USER_ONLY
6879 if (tcg_enabled()) {
6880 cpu->cpu_as_mem = g_new(MemoryRegion, 1);
6881 cpu->cpu_as_root = g_new(MemoryRegion, 1);
6883 /* Outer container... */
6884 memory_region_init(cpu->cpu_as_root, OBJECT(cpu), "memory", ~0ull);
6885 memory_region_set_enabled(cpu->cpu_as_root, true);
6887 /* ... with two regions inside: normal system memory with low
6888 * priority, and...
6890 memory_region_init_alias(cpu->cpu_as_mem, OBJECT(cpu), "memory",
6891 get_system_memory(), 0, ~0ull);
6892 memory_region_add_subregion_overlap(cpu->cpu_as_root, 0, cpu->cpu_as_mem, 0);
6893 memory_region_set_enabled(cpu->cpu_as_mem, true);
6895 cs->num_ases = 2;
6896 cpu_address_space_init(cs, 0, "cpu-memory", cs->memory);
6897 cpu_address_space_init(cs, 1, "cpu-smm", cpu->cpu_as_root);
6899 /* ... SMRAM with higher priority, linked from /machine/smram. */
6900 cpu->machine_done.notify = x86_cpu_machine_done;
6901 qemu_add_machine_init_done_notifier(&cpu->machine_done);
6903 #endif
6905 qemu_init_vcpu(cs);
6908 * Most Intel and certain AMD CPUs support hyperthreading. Even though QEMU
6909 * fixes this issue by adjusting CPUID_0000_0001_EBX and CPUID_8000_0008_ECX
6910 * based on inputs (sockets,cores,threads), it is still better to give
6911 * users a warning.
6913 * NOTE: the following code has to follow qemu_init_vcpu(). Otherwise
6914 * cs->nr_threads hasn't be populated yet and the checking is incorrect.
6916 if (IS_AMD_CPU(env) &&
6917 !(env->features[FEAT_8000_0001_ECX] & CPUID_EXT3_TOPOEXT) &&
6918 cs->nr_threads > 1 && !ht_warned) {
6919 warn_report("This family of AMD CPU doesn't support "
6920 "hyperthreading(%d)",
6921 cs->nr_threads);
6922 error_printf("Please configure -smp options properly"
6923 " or try enabling topoext feature.\n");
6924 ht_warned = true;
6927 x86_cpu_apic_realize(cpu, &local_err);
6928 if (local_err != NULL) {
6929 goto out;
6931 cpu_reset(cs);
6933 xcc->parent_realize(dev, &local_err);
6935 out:
6936 if (local_err != NULL) {
6937 error_propagate(errp, local_err);
6938 return;
6942 static void x86_cpu_unrealizefn(DeviceState *dev)
6944 X86CPU *cpu = X86_CPU(dev);
6945 X86CPUClass *xcc = X86_CPU_GET_CLASS(dev);
6947 #ifndef CONFIG_USER_ONLY
6948 cpu_remove_sync(CPU(dev));
6949 qemu_unregister_reset(x86_cpu_machine_reset_cb, dev);
6950 #endif
6952 if (cpu->apic_state) {
6953 object_unparent(OBJECT(cpu->apic_state));
6954 cpu->apic_state = NULL;
6957 xcc->parent_unrealize(dev);
6960 typedef struct BitProperty {
6961 FeatureWord w;
6962 uint64_t mask;
6963 } BitProperty;
6965 static void x86_cpu_get_bit_prop(Object *obj, Visitor *v, const char *name,
6966 void *opaque, Error **errp)
6968 X86CPU *cpu = X86_CPU(obj);
6969 BitProperty *fp = opaque;
6970 uint64_t f = cpu->env.features[fp->w];
6971 bool value = (f & fp->mask) == fp->mask;
6972 visit_type_bool(v, name, &value, errp);
6975 static void x86_cpu_set_bit_prop(Object *obj, Visitor *v, const char *name,
6976 void *opaque, Error **errp)
6978 DeviceState *dev = DEVICE(obj);
6979 X86CPU *cpu = X86_CPU(obj);
6980 BitProperty *fp = opaque;
6981 bool value;
6983 if (dev->realized) {
6984 qdev_prop_set_after_realize(dev, name, errp);
6985 return;
6988 if (!visit_type_bool(v, name, &value, errp)) {
6989 return;
6992 if (value) {
6993 cpu->env.features[fp->w] |= fp->mask;
6994 } else {
6995 cpu->env.features[fp->w] &= ~fp->mask;
6997 cpu->env.user_features[fp->w] |= fp->mask;
7000 /* Register a boolean property to get/set a single bit in a uint32_t field.
7002 * The same property name can be registered multiple times to make it affect
7003 * multiple bits in the same FeatureWord. In that case, the getter will return
7004 * true only if all bits are set.
7006 static void x86_cpu_register_bit_prop(X86CPUClass *xcc,
7007 const char *prop_name,
7008 FeatureWord w,
7009 int bitnr)
7011 ObjectClass *oc = OBJECT_CLASS(xcc);
7012 BitProperty *fp;
7013 ObjectProperty *op;
7014 uint64_t mask = (1ULL << bitnr);
7016 op = object_class_property_find(oc, prop_name);
7017 if (op) {
7018 fp = op->opaque;
7019 assert(fp->w == w);
7020 fp->mask |= mask;
7021 } else {
7022 fp = g_new0(BitProperty, 1);
7023 fp->w = w;
7024 fp->mask = mask;
7025 object_class_property_add(oc, prop_name, "bool",
7026 x86_cpu_get_bit_prop,
7027 x86_cpu_set_bit_prop,
7028 NULL, fp);
7032 static void x86_cpu_register_feature_bit_props(X86CPUClass *xcc,
7033 FeatureWord w,
7034 int bitnr)
7036 FeatureWordInfo *fi = &feature_word_info[w];
7037 const char *name = fi->feat_names[bitnr];
7039 if (!name) {
7040 return;
7043 /* Property names should use "-" instead of "_".
7044 * Old names containing underscores are registered as aliases
7045 * using object_property_add_alias()
7047 assert(!strchr(name, '_'));
7048 /* aliases don't use "|" delimiters anymore, they are registered
7049 * manually using object_property_add_alias() */
7050 assert(!strchr(name, '|'));
7051 x86_cpu_register_bit_prop(xcc, name, w, bitnr);
7054 #if !defined(CONFIG_USER_ONLY)
7055 static GuestPanicInformation *x86_cpu_get_crash_info(CPUState *cs)
7057 X86CPU *cpu = X86_CPU(cs);
7058 CPUX86State *env = &cpu->env;
7059 GuestPanicInformation *panic_info = NULL;
7061 if (env->features[FEAT_HYPERV_EDX] & HV_GUEST_CRASH_MSR_AVAILABLE) {
7062 panic_info = g_malloc0(sizeof(GuestPanicInformation));
7064 panic_info->type = GUEST_PANIC_INFORMATION_TYPE_HYPER_V;
7066 assert(HV_CRASH_PARAMS >= 5);
7067 panic_info->u.hyper_v.arg1 = env->msr_hv_crash_params[0];
7068 panic_info->u.hyper_v.arg2 = env->msr_hv_crash_params[1];
7069 panic_info->u.hyper_v.arg3 = env->msr_hv_crash_params[2];
7070 panic_info->u.hyper_v.arg4 = env->msr_hv_crash_params[3];
7071 panic_info->u.hyper_v.arg5 = env->msr_hv_crash_params[4];
7074 return panic_info;
7076 static void x86_cpu_get_crash_info_qom(Object *obj, Visitor *v,
7077 const char *name, void *opaque,
7078 Error **errp)
7080 CPUState *cs = CPU(obj);
7081 GuestPanicInformation *panic_info;
7083 if (!cs->crash_occurred) {
7084 error_setg(errp, "No crash occured");
7085 return;
7088 panic_info = x86_cpu_get_crash_info(cs);
7089 if (panic_info == NULL) {
7090 error_setg(errp, "No crash information");
7091 return;
7094 visit_type_GuestPanicInformation(v, "crash-information", &panic_info,
7095 errp);
7096 qapi_free_GuestPanicInformation(panic_info);
7098 #endif /* !CONFIG_USER_ONLY */
7100 static void x86_cpu_initfn(Object *obj)
7102 X86CPU *cpu = X86_CPU(obj);
7103 X86CPUClass *xcc = X86_CPU_GET_CLASS(obj);
7104 CPUX86State *env = &cpu->env;
7106 env->nr_dies = 1;
7107 cpu_set_cpustate_pointers(cpu);
7109 object_property_add(obj, "feature-words", "X86CPUFeatureWordInfo",
7110 x86_cpu_get_feature_words,
7111 NULL, NULL, (void *)env->features);
7112 object_property_add(obj, "filtered-features", "X86CPUFeatureWordInfo",
7113 x86_cpu_get_feature_words,
7114 NULL, NULL, (void *)cpu->filtered_features);
7116 object_property_add_alias(obj, "sse3", obj, "pni");
7117 object_property_add_alias(obj, "pclmuldq", obj, "pclmulqdq");
7118 object_property_add_alias(obj, "sse4-1", obj, "sse4.1");
7119 object_property_add_alias(obj, "sse4-2", obj, "sse4.2");
7120 object_property_add_alias(obj, "xd", obj, "nx");
7121 object_property_add_alias(obj, "ffxsr", obj, "fxsr-opt");
7122 object_property_add_alias(obj, "i64", obj, "lm");
7124 object_property_add_alias(obj, "ds_cpl", obj, "ds-cpl");
7125 object_property_add_alias(obj, "tsc_adjust", obj, "tsc-adjust");
7126 object_property_add_alias(obj, "fxsr_opt", obj, "fxsr-opt");
7127 object_property_add_alias(obj, "lahf_lm", obj, "lahf-lm");
7128 object_property_add_alias(obj, "cmp_legacy", obj, "cmp-legacy");
7129 object_property_add_alias(obj, "nodeid_msr", obj, "nodeid-msr");
7130 object_property_add_alias(obj, "perfctr_core", obj, "perfctr-core");
7131 object_property_add_alias(obj, "perfctr_nb", obj, "perfctr-nb");
7132 object_property_add_alias(obj, "kvm_nopiodelay", obj, "kvm-nopiodelay");
7133 object_property_add_alias(obj, "kvm_mmu", obj, "kvm-mmu");
7134 object_property_add_alias(obj, "kvm_asyncpf", obj, "kvm-asyncpf");
7135 object_property_add_alias(obj, "kvm_asyncpf_int", obj, "kvm-asyncpf-int");
7136 object_property_add_alias(obj, "kvm_steal_time", obj, "kvm-steal-time");
7137 object_property_add_alias(obj, "kvm_pv_eoi", obj, "kvm-pv-eoi");
7138 object_property_add_alias(obj, "kvm_pv_unhalt", obj, "kvm-pv-unhalt");
7139 object_property_add_alias(obj, "kvm_poll_control", obj, "kvm-poll-control");
7140 object_property_add_alias(obj, "svm_lock", obj, "svm-lock");
7141 object_property_add_alias(obj, "nrip_save", obj, "nrip-save");
7142 object_property_add_alias(obj, "tsc_scale", obj, "tsc-scale");
7143 object_property_add_alias(obj, "vmcb_clean", obj, "vmcb-clean");
7144 object_property_add_alias(obj, "pause_filter", obj, "pause-filter");
7145 object_property_add_alias(obj, "sse4_1", obj, "sse4.1");
7146 object_property_add_alias(obj, "sse4_2", obj, "sse4.2");
7148 if (xcc->model) {
7149 x86_cpu_load_model(cpu, xcc->model);
7153 static int64_t x86_cpu_get_arch_id(CPUState *cs)
7155 X86CPU *cpu = X86_CPU(cs);
7157 return cpu->apic_id;
7160 static bool x86_cpu_get_paging_enabled(const CPUState *cs)
7162 X86CPU *cpu = X86_CPU(cs);
7164 return cpu->env.cr[0] & CR0_PG_MASK;
7167 static void x86_cpu_set_pc(CPUState *cs, vaddr value)
7169 X86CPU *cpu = X86_CPU(cs);
7171 cpu->env.eip = value;
7174 int x86_cpu_pending_interrupt(CPUState *cs, int interrupt_request)
7176 X86CPU *cpu = X86_CPU(cs);
7177 CPUX86State *env = &cpu->env;
7179 #if !defined(CONFIG_USER_ONLY)
7180 if (interrupt_request & CPU_INTERRUPT_POLL) {
7181 return CPU_INTERRUPT_POLL;
7183 #endif
7184 if (interrupt_request & CPU_INTERRUPT_SIPI) {
7185 return CPU_INTERRUPT_SIPI;
7188 if (env->hflags2 & HF2_GIF_MASK) {
7189 if ((interrupt_request & CPU_INTERRUPT_SMI) &&
7190 !(env->hflags & HF_SMM_MASK)) {
7191 return CPU_INTERRUPT_SMI;
7192 } else if ((interrupt_request & CPU_INTERRUPT_NMI) &&
7193 !(env->hflags2 & HF2_NMI_MASK)) {
7194 return CPU_INTERRUPT_NMI;
7195 } else if (interrupt_request & CPU_INTERRUPT_MCE) {
7196 return CPU_INTERRUPT_MCE;
7197 } else if ((interrupt_request & CPU_INTERRUPT_HARD) &&
7198 (((env->hflags2 & HF2_VINTR_MASK) &&
7199 (env->hflags2 & HF2_HIF_MASK)) ||
7200 (!(env->hflags2 & HF2_VINTR_MASK) &&
7201 (env->eflags & IF_MASK &&
7202 !(env->hflags & HF_INHIBIT_IRQ_MASK))))) {
7203 return CPU_INTERRUPT_HARD;
7204 #if !defined(CONFIG_USER_ONLY)
7205 } else if ((interrupt_request & CPU_INTERRUPT_VIRQ) &&
7206 (env->eflags & IF_MASK) &&
7207 !(env->hflags & HF_INHIBIT_IRQ_MASK)) {
7208 return CPU_INTERRUPT_VIRQ;
7209 #endif
7213 return 0;
7216 static bool x86_cpu_has_work(CPUState *cs)
7218 return x86_cpu_pending_interrupt(cs, cs->interrupt_request) != 0;
7221 static void x86_disas_set_info(CPUState *cs, disassemble_info *info)
7223 X86CPU *cpu = X86_CPU(cs);
7224 CPUX86State *env = &cpu->env;
7226 info->mach = (env->hflags & HF_CS64_MASK ? bfd_mach_x86_64
7227 : env->hflags & HF_CS32_MASK ? bfd_mach_i386_i386
7228 : bfd_mach_i386_i8086);
7229 info->print_insn = print_insn_i386;
7231 info->cap_arch = CS_ARCH_X86;
7232 info->cap_mode = (env->hflags & HF_CS64_MASK ? CS_MODE_64
7233 : env->hflags & HF_CS32_MASK ? CS_MODE_32
7234 : CS_MODE_16);
7235 info->cap_insn_unit = 1;
7236 info->cap_insn_split = 8;
7239 void x86_update_hflags(CPUX86State *env)
7241 uint32_t hflags;
7242 #define HFLAG_COPY_MASK \
7243 ~( HF_CPL_MASK | HF_PE_MASK | HF_MP_MASK | HF_EM_MASK | \
7244 HF_TS_MASK | HF_TF_MASK | HF_VM_MASK | HF_IOPL_MASK | \
7245 HF_OSFXSR_MASK | HF_LMA_MASK | HF_CS32_MASK | \
7246 HF_SS32_MASK | HF_CS64_MASK | HF_ADDSEG_MASK)
7248 hflags = env->hflags & HFLAG_COPY_MASK;
7249 hflags |= (env->segs[R_SS].flags >> DESC_DPL_SHIFT) & HF_CPL_MASK;
7250 hflags |= (env->cr[0] & CR0_PE_MASK) << (HF_PE_SHIFT - CR0_PE_SHIFT);
7251 hflags |= (env->cr[0] << (HF_MP_SHIFT - CR0_MP_SHIFT)) &
7252 (HF_MP_MASK | HF_EM_MASK | HF_TS_MASK);
7253 hflags |= (env->eflags & (HF_TF_MASK | HF_VM_MASK | HF_IOPL_MASK));
7255 if (env->cr[4] & CR4_OSFXSR_MASK) {
7256 hflags |= HF_OSFXSR_MASK;
7259 if (env->efer & MSR_EFER_LMA) {
7260 hflags |= HF_LMA_MASK;
7263 if ((hflags & HF_LMA_MASK) && (env->segs[R_CS].flags & DESC_L_MASK)) {
7264 hflags |= HF_CS32_MASK | HF_SS32_MASK | HF_CS64_MASK;
7265 } else {
7266 hflags |= (env->segs[R_CS].flags & DESC_B_MASK) >>
7267 (DESC_B_SHIFT - HF_CS32_SHIFT);
7268 hflags |= (env->segs[R_SS].flags & DESC_B_MASK) >>
7269 (DESC_B_SHIFT - HF_SS32_SHIFT);
7270 if (!(env->cr[0] & CR0_PE_MASK) || (env->eflags & VM_MASK) ||
7271 !(hflags & HF_CS32_MASK)) {
7272 hflags |= HF_ADDSEG_MASK;
7273 } else {
7274 hflags |= ((env->segs[R_DS].base | env->segs[R_ES].base |
7275 env->segs[R_SS].base) != 0) << HF_ADDSEG_SHIFT;
7278 env->hflags = hflags;
7281 static Property x86_cpu_properties[] = {
7282 #ifdef CONFIG_USER_ONLY
7283 /* apic_id = 0 by default for *-user, see commit 9886e834 */
7284 DEFINE_PROP_UINT32("apic-id", X86CPU, apic_id, 0),
7285 DEFINE_PROP_INT32("thread-id", X86CPU, thread_id, 0),
7286 DEFINE_PROP_INT32("core-id", X86CPU, core_id, 0),
7287 DEFINE_PROP_INT32("die-id", X86CPU, die_id, 0),
7288 DEFINE_PROP_INT32("socket-id", X86CPU, socket_id, 0),
7289 #else
7290 DEFINE_PROP_UINT32("apic-id", X86CPU, apic_id, UNASSIGNED_APIC_ID),
7291 DEFINE_PROP_INT32("thread-id", X86CPU, thread_id, -1),
7292 DEFINE_PROP_INT32("core-id", X86CPU, core_id, -1),
7293 DEFINE_PROP_INT32("die-id", X86CPU, die_id, -1),
7294 DEFINE_PROP_INT32("socket-id", X86CPU, socket_id, -1),
7295 #endif
7296 DEFINE_PROP_INT32("node-id", X86CPU, node_id, CPU_UNSET_NUMA_NODE_ID),
7297 DEFINE_PROP_BOOL("pmu", X86CPU, enable_pmu, false),
7299 DEFINE_PROP_UINT32("hv-spinlocks", X86CPU, hyperv_spinlock_attempts,
7300 HYPERV_SPINLOCK_NEVER_NOTIFY),
7301 DEFINE_PROP_BIT64("hv-relaxed", X86CPU, hyperv_features,
7302 HYPERV_FEAT_RELAXED, 0),
7303 DEFINE_PROP_BIT64("hv-vapic", X86CPU, hyperv_features,
7304 HYPERV_FEAT_VAPIC, 0),
7305 DEFINE_PROP_BIT64("hv-time", X86CPU, hyperv_features,
7306 HYPERV_FEAT_TIME, 0),
7307 DEFINE_PROP_BIT64("hv-crash", X86CPU, hyperv_features,
7308 HYPERV_FEAT_CRASH, 0),
7309 DEFINE_PROP_BIT64("hv-reset", X86CPU, hyperv_features,
7310 HYPERV_FEAT_RESET, 0),
7311 DEFINE_PROP_BIT64("hv-vpindex", X86CPU, hyperv_features,
7312 HYPERV_FEAT_VPINDEX, 0),
7313 DEFINE_PROP_BIT64("hv-runtime", X86CPU, hyperv_features,
7314 HYPERV_FEAT_RUNTIME, 0),
7315 DEFINE_PROP_BIT64("hv-synic", X86CPU, hyperv_features,
7316 HYPERV_FEAT_SYNIC, 0),
7317 DEFINE_PROP_BIT64("hv-stimer", X86CPU, hyperv_features,
7318 HYPERV_FEAT_STIMER, 0),
7319 DEFINE_PROP_BIT64("hv-frequencies", X86CPU, hyperv_features,
7320 HYPERV_FEAT_FREQUENCIES, 0),
7321 DEFINE_PROP_BIT64("hv-reenlightenment", X86CPU, hyperv_features,
7322 HYPERV_FEAT_REENLIGHTENMENT, 0),
7323 DEFINE_PROP_BIT64("hv-tlbflush", X86CPU, hyperv_features,
7324 HYPERV_FEAT_TLBFLUSH, 0),
7325 DEFINE_PROP_BIT64("hv-evmcs", X86CPU, hyperv_features,
7326 HYPERV_FEAT_EVMCS, 0),
7327 DEFINE_PROP_BIT64("hv-ipi", X86CPU, hyperv_features,
7328 HYPERV_FEAT_IPI, 0),
7329 DEFINE_PROP_BIT64("hv-stimer-direct", X86CPU, hyperv_features,
7330 HYPERV_FEAT_STIMER_DIRECT, 0),
7331 DEFINE_PROP_ON_OFF_AUTO("hv-no-nonarch-coresharing", X86CPU,
7332 hyperv_no_nonarch_cs, ON_OFF_AUTO_OFF),
7333 DEFINE_PROP_BOOL("hv-passthrough", X86CPU, hyperv_passthrough, false),
7335 DEFINE_PROP_BOOL("check", X86CPU, check_cpuid, true),
7336 DEFINE_PROP_BOOL("enforce", X86CPU, enforce_cpuid, false),
7337 DEFINE_PROP_BOOL("x-force-features", X86CPU, force_features, false),
7338 DEFINE_PROP_BOOL("kvm", X86CPU, expose_kvm, true),
7339 DEFINE_PROP_UINT32("phys-bits", X86CPU, phys_bits, 0),
7340 DEFINE_PROP_BOOL("host-phys-bits", X86CPU, host_phys_bits, false),
7341 DEFINE_PROP_UINT8("host-phys-bits-limit", X86CPU, host_phys_bits_limit, 0),
7342 DEFINE_PROP_BOOL("fill-mtrr-mask", X86CPU, fill_mtrr_mask, true),
7343 DEFINE_PROP_UINT32("level-func7", X86CPU, env.cpuid_level_func7,
7344 UINT32_MAX),
7345 DEFINE_PROP_UINT32("level", X86CPU, env.cpuid_level, UINT32_MAX),
7346 DEFINE_PROP_UINT32("xlevel", X86CPU, env.cpuid_xlevel, UINT32_MAX),
7347 DEFINE_PROP_UINT32("xlevel2", X86CPU, env.cpuid_xlevel2, UINT32_MAX),
7348 DEFINE_PROP_UINT32("min-level", X86CPU, env.cpuid_min_level, 0),
7349 DEFINE_PROP_UINT32("min-xlevel", X86CPU, env.cpuid_min_xlevel, 0),
7350 DEFINE_PROP_UINT32("min-xlevel2", X86CPU, env.cpuid_min_xlevel2, 0),
7351 DEFINE_PROP_UINT64("ucode-rev", X86CPU, ucode_rev, 0),
7352 DEFINE_PROP_BOOL("full-cpuid-auto-level", X86CPU, full_cpuid_auto_level, true),
7353 DEFINE_PROP_STRING("hv-vendor-id", X86CPU, hyperv_vendor),
7354 DEFINE_PROP_BOOL("cpuid-0xb", X86CPU, enable_cpuid_0xb, true),
7355 DEFINE_PROP_BOOL("lmce", X86CPU, enable_lmce, false),
7356 DEFINE_PROP_BOOL("l3-cache", X86CPU, enable_l3_cache, true),
7357 DEFINE_PROP_BOOL("kvm-no-smi-migration", X86CPU, kvm_no_smi_migration,
7358 false),
7359 DEFINE_PROP_BOOL("vmware-cpuid-freq", X86CPU, vmware_cpuid_freq, true),
7360 DEFINE_PROP_BOOL("tcg-cpuid", X86CPU, expose_tcg, true),
7361 DEFINE_PROP_BOOL("x-migrate-smi-count", X86CPU, migrate_smi_count,
7362 true),
7364 * lecacy_cache defaults to true unless the CPU model provides its
7365 * own cache information (see x86_cpu_load_def()).
7367 DEFINE_PROP_BOOL("legacy-cache", X86CPU, legacy_cache, true),
7370 * From "Requirements for Implementing the Microsoft
7371 * Hypervisor Interface":
7372 * https://docs.microsoft.com/en-us/virtualization/hyper-v-on-windows/reference/tlfs
7374 * "Starting with Windows Server 2012 and Windows 8, if
7375 * CPUID.40000005.EAX contains a value of -1, Windows assumes that
7376 * the hypervisor imposes no specific limit to the number of VPs.
7377 * In this case, Windows Server 2012 guest VMs may use more than
7378 * 64 VPs, up to the maximum supported number of processors applicable
7379 * to the specific Windows version being used."
7381 DEFINE_PROP_INT32("x-hv-max-vps", X86CPU, hv_max_vps, -1),
7382 DEFINE_PROP_BOOL("x-hv-synic-kvm-only", X86CPU, hyperv_synic_kvm_only,
7383 false),
7384 DEFINE_PROP_BOOL("x-intel-pt-auto-level", X86CPU, intel_pt_auto_level,
7385 true),
7386 DEFINE_PROP_END_OF_LIST()
7389 static void x86_cpu_common_class_init(ObjectClass *oc, void *data)
7391 X86CPUClass *xcc = X86_CPU_CLASS(oc);
7392 CPUClass *cc = CPU_CLASS(oc);
7393 DeviceClass *dc = DEVICE_CLASS(oc);
7394 FeatureWord w;
7396 device_class_set_parent_realize(dc, x86_cpu_realizefn,
7397 &xcc->parent_realize);
7398 device_class_set_parent_unrealize(dc, x86_cpu_unrealizefn,
7399 &xcc->parent_unrealize);
7400 device_class_set_props(dc, x86_cpu_properties);
7402 device_class_set_parent_reset(dc, x86_cpu_reset, &xcc->parent_reset);
7403 cc->reset_dump_flags = CPU_DUMP_FPU | CPU_DUMP_CCOP;
7405 cc->class_by_name = x86_cpu_class_by_name;
7406 cc->parse_features = x86_cpu_parse_featurestr;
7407 cc->has_work = x86_cpu_has_work;
7409 #ifdef CONFIG_TCG
7410 tcg_cpu_common_class_init(cc);
7411 #endif /* CONFIG_TCG */
7413 cc->dump_state = x86_cpu_dump_state;
7414 cc->set_pc = x86_cpu_set_pc;
7415 cc->gdb_read_register = x86_cpu_gdb_read_register;
7416 cc->gdb_write_register = x86_cpu_gdb_write_register;
7417 cc->get_arch_id = x86_cpu_get_arch_id;
7418 cc->get_paging_enabled = x86_cpu_get_paging_enabled;
7420 #ifndef CONFIG_USER_ONLY
7421 cc->asidx_from_attrs = x86_asidx_from_attrs;
7422 cc->get_memory_mapping = x86_cpu_get_memory_mapping;
7423 cc->get_phys_page_attrs_debug = x86_cpu_get_phys_page_attrs_debug;
7424 cc->get_crash_info = x86_cpu_get_crash_info;
7425 cc->write_elf64_note = x86_cpu_write_elf64_note;
7426 cc->write_elf64_qemunote = x86_cpu_write_elf64_qemunote;
7427 cc->write_elf32_note = x86_cpu_write_elf32_note;
7428 cc->write_elf32_qemunote = x86_cpu_write_elf32_qemunote;
7429 cc->vmsd = &vmstate_x86_cpu;
7430 #endif /* !CONFIG_USER_ONLY */
7432 cc->gdb_arch_name = x86_gdb_arch_name;
7433 #ifdef TARGET_X86_64
7434 cc->gdb_core_xml_file = "i386-64bit.xml";
7435 cc->gdb_num_core_regs = 66;
7436 #else
7437 cc->gdb_core_xml_file = "i386-32bit.xml";
7438 cc->gdb_num_core_regs = 50;
7439 #endif
7440 cc->disas_set_info = x86_disas_set_info;
7442 dc->user_creatable = true;
7444 object_class_property_add(oc, "family", "int",
7445 x86_cpuid_version_get_family,
7446 x86_cpuid_version_set_family, NULL, NULL);
7447 object_class_property_add(oc, "model", "int",
7448 x86_cpuid_version_get_model,
7449 x86_cpuid_version_set_model, NULL, NULL);
7450 object_class_property_add(oc, "stepping", "int",
7451 x86_cpuid_version_get_stepping,
7452 x86_cpuid_version_set_stepping, NULL, NULL);
7453 object_class_property_add_str(oc, "vendor",
7454 x86_cpuid_get_vendor,
7455 x86_cpuid_set_vendor);
7456 object_class_property_add_str(oc, "model-id",
7457 x86_cpuid_get_model_id,
7458 x86_cpuid_set_model_id);
7459 object_class_property_add(oc, "tsc-frequency", "int",
7460 x86_cpuid_get_tsc_freq,
7461 x86_cpuid_set_tsc_freq, NULL, NULL);
7463 * The "unavailable-features" property has the same semantics as
7464 * CpuDefinitionInfo.unavailable-features on the "query-cpu-definitions"
7465 * QMP command: they list the features that would have prevented the
7466 * CPU from running if the "enforce" flag was set.
7468 object_class_property_add(oc, "unavailable-features", "strList",
7469 x86_cpu_get_unavailable_features,
7470 NULL, NULL, NULL);
7472 #if !defined(CONFIG_USER_ONLY)
7473 object_class_property_add(oc, "crash-information", "GuestPanicInformation",
7474 x86_cpu_get_crash_info_qom, NULL, NULL, NULL);
7475 #endif
7477 for (w = 0; w < FEATURE_WORDS; w++) {
7478 int bitnr;
7479 for (bitnr = 0; bitnr < 64; bitnr++) {
7480 x86_cpu_register_feature_bit_props(xcc, w, bitnr);
7485 static const TypeInfo x86_cpu_type_info = {
7486 .name = TYPE_X86_CPU,
7487 .parent = TYPE_CPU,
7488 .instance_size = sizeof(X86CPU),
7489 .instance_init = x86_cpu_initfn,
7490 .abstract = true,
7491 .class_size = sizeof(X86CPUClass),
7492 .class_init = x86_cpu_common_class_init,
7496 /* "base" CPU model, used by query-cpu-model-expansion */
7497 static void x86_cpu_base_class_init(ObjectClass *oc, void *data)
7499 X86CPUClass *xcc = X86_CPU_CLASS(oc);
7501 xcc->static_model = true;
7502 xcc->migration_safe = true;
7503 xcc->model_description = "base CPU model type with no features enabled";
7504 xcc->ordering = 8;
7507 static const TypeInfo x86_base_cpu_type_info = {
7508 .name = X86_CPU_TYPE_NAME("base"),
7509 .parent = TYPE_X86_CPU,
7510 .class_init = x86_cpu_base_class_init,
7513 static void x86_cpu_register_types(void)
7515 int i;
7517 type_register_static(&x86_cpu_type_info);
7518 for (i = 0; i < ARRAY_SIZE(builtin_x86_defs); i++) {
7519 x86_register_cpudef_types(&builtin_x86_defs[i]);
7521 type_register_static(&max_x86_cpu_type_info);
7522 type_register_static(&x86_base_cpu_type_info);
7523 #if defined(CONFIG_KVM) || defined(CONFIG_HVF)
7524 type_register_static(&host_x86_cpu_type_info);
7525 #endif
7528 type_init(x86_cpu_register_types)