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