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