Message ID | 1357870690-12680-3-git-send-email-ehabkost@redhat.com |
---|---|
State | New |
Headers | show |
Reviewed-by: Li Guang <lig.fnst@cn.fujitsu.com> 在 2013-01-11五的 00:18 -0200,Eduardo Habkost写道: > This replaces the feature-bit fields on both X86CPU and x86_def_t > structs with an array. > > With this, we will be able to simplify code that simply does the same > operation on all feature words (e.g. kvm_check_features_against_host(), > filter_features_for_kvm(), add_flagname_to_bitmaps(), and CPU > feature-bit property lookup/registration). > > This should also help avoid bugs like the ones introduced when we added > cpuid_7_0_ebx_features. Today, adding a new feature word to the code > requires chaning 5 or 6 different places in the code, and it's very easy > to miss a problem when we forget to update one of those parts. See, for > example: > > * The bug solved by commit ffa8c11f0bbf47e1b7a3a62f97bc1da591c6734a; > * The fact that check_features_against_host() wasn't checking all > feature words as it is supposed to, until very recently. > > Signed-off-by: Eduardo Habkost <ehabkost@redhat.com> > --- > This patch was created solely using a sed script and no manual changes, > to try to avoid mistakes while converting the code, and make it easier > to rebase if necessary. The sed script can be seen at: > https://gist.github.com/4271991 > --- > bsd-user/elfload.c | 2 +- > bsd-user/main.c | 4 +- > hw/kvm/clock.c | 2 +- > linux-user/elfload.c | 2 +- > linux-user/main.c | 4 +- > target-i386/cpu.c | 592 ++++++++++++++++++++++++---------------------- > target-i386/cpu.h | 15 +- > target-i386/helper.c | 4 +- > target-i386/kvm.c | 5 +- > target-i386/misc_helper.c | 14 +- > target-i386/translate.c | 10 +- > 11 files changed, 332 insertions(+), 322 deletions(-) > > diff --git a/bsd-user/elfload.c b/bsd-user/elfload.c > index a6cd3ab..44e1568 100644 > --- a/bsd-user/elfload.c > +++ b/bsd-user/elfload.c > @@ -110,7 +110,7 @@ static const char *get_elf_platform(void) > > static uint32_t get_elf_hwcap(void) > { > - return thread_env->cpuid_features; > + return thread_env->features[FEAT_1_EDX]; > } > > #ifdef TARGET_X86_64 > diff --git a/bsd-user/main.c b/bsd-user/main.c > index 1dc0330..8b8b1f1 100644 > --- a/bsd-user/main.c > +++ b/bsd-user/main.c > @@ -1010,13 +1010,13 @@ int main(int argc, char **argv) > > env->cr[0] = CR0_PG_MASK | CR0_WP_MASK | CR0_PE_MASK; > env->hflags |= HF_PE_MASK; > - if (env->cpuid_features & CPUID_SSE) { > + if (env->features[FEAT_1_EDX] & CPUID_SSE) { > env->cr[4] |= CR4_OSFXSR_MASK; > env->hflags |= HF_OSFXSR_MASK; > } > #ifndef TARGET_ABI32 > /* enable 64 bit mode if possible */ > - if (!(env->cpuid_ext2_features & CPUID_EXT2_LM)) { > + if (!(env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_LM)) { > fprintf(stderr, "The selected x86 CPU does not support 64 bit mode\n"); > exit(1); > } > diff --git a/hw/kvm/clock.c b/hw/kvm/clock.c > index be24973..6d0777a 100644 > --- a/hw/kvm/clock.c > +++ b/hw/kvm/clock.c > @@ -129,7 +129,7 @@ static TypeInfo kvmclock_info = { > void kvmclock_create(void) > { > if (kvm_enabled() && > - first_cpu->cpuid_kvm_features & ((1ULL << KVM_FEATURE_CLOCKSOURCE) | > + first_cpu->features[FEAT_KVM] & ((1ULL << KVM_FEATURE_CLOCKSOURCE) | > (1ULL << KVM_FEATURE_CLOCKSOURCE2))) { > sysbus_create_simple("kvmclock", -1, NULL); > } > diff --git a/linux-user/elfload.c b/linux-user/elfload.c > index 89db49c..04755de 100644 > --- a/linux-user/elfload.c > +++ b/linux-user/elfload.c > @@ -130,7 +130,7 @@ static const char *get_elf_platform(void) > > static uint32_t get_elf_hwcap(void) > { > - return thread_env->cpuid_features; > + return thread_env->features[FEAT_1_EDX]; > } > > #ifdef TARGET_X86_64 > diff --git a/linux-user/main.c b/linux-user/main.c > index 9ade1bf..faed8c8 100644 > --- a/linux-user/main.c > +++ b/linux-user/main.c > @@ -3630,13 +3630,13 @@ int main(int argc, char **argv, char **envp) > > env->cr[0] = CR0_PG_MASK | CR0_WP_MASK | CR0_PE_MASK; > env->hflags |= HF_PE_MASK; > - if (env->cpuid_features & CPUID_SSE) { > + if (env->features[FEAT_1_EDX] & CPUID_SSE) { > env->cr[4] |= CR4_OSFXSR_MASK; > env->hflags |= HF_OSFXSR_MASK; > } > #ifndef TARGET_ABI32 > /* enable 64 bit mode if possible */ > - if (!(env->cpuid_ext2_features & CPUID_EXT2_LM)) { > + if (!(env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_LM)) { > fprintf(stderr, "The selected x86 CPU does not support 64 bit mode\n"); > exit(1); > } > diff --git a/target-i386/cpu.c b/target-i386/cpu.c > index 0b44dea..f4878bf 100644 > --- a/target-i386/cpu.c > +++ b/target-i386/cpu.c > @@ -340,22 +340,15 @@ static void add_flagname_to_bitmaps(const char *flagname, > typedef struct x86_def_t { > struct x86_def_t *next; > const char *name; > - uint32_t level; > + uint32_t level, xlevel, xlevel2; > + FeatureWordArray features; > uint32_t vendor1, vendor2, vendor3; > int family; > int model; > int stepping; > int tsc_khz; > - uint32_t features, ext_features, ext2_features, ext3_features; > - uint32_t kvm_features, svm_features; > - uint32_t xlevel; > char model_id[48]; > int vendor_override; > - /* Store the results of Centaur's CPUID instructions */ > - uint32_t ext4_features; > - uint32_t xlevel2; > - /* The feature bits on CPUID[EAX=7,ECX=0].EBX */ > - uint32_t cpuid_7_0_ebx_features; > } x86_def_t; > > #define I486_FEATURES (CPUID_FP87 | CPUID_VME | CPUID_PSE) > @@ -412,13 +405,14 @@ static x86_def_t builtin_x86_defs[] = { > .family = 6, > .model = 2, > .stepping = 3, > - .features = PPRO_FEATURES | > - CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | > - CPUID_PSE36, > - .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_CX16 | CPUID_EXT_POPCNT, > - .ext2_features = (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | > - CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX, > - .ext3_features = CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM | > + .features[FEAT_1_EDX] = PPRO_FEATURES | CPUID_MTRR | CPUID_CLFLUSH | > + CPUID_MCA | CPUID_PSE36, > + .features[FEAT_1_ECX] = CPUID_EXT_SSE3 | CPUID_EXT_CX16 | > + CPUID_EXT_POPCNT, > + .features[FEAT_8000_0001_EDX] = > + (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | CPUID_EXT2_LM | > + CPUID_EXT2_SYSCALL | CPUID_EXT2_NX, > + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM | > CPUID_EXT3_ABM | CPUID_EXT3_SSE4A, > .xlevel = 0x8000000A, > }, > @@ -431,22 +425,22 @@ static x86_def_t builtin_x86_defs[] = { > .family = 16, > .model = 2, > .stepping = 3, > - .features = PPRO_FEATURES | > - CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | > - CPUID_PSE36 | CPUID_VME | CPUID_HT, > - .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_CX16 | > - CPUID_EXT_POPCNT, > - .ext2_features = (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | > - CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX | > - CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT | CPUID_EXT2_MMXEXT | > - CPUID_EXT2_FFXSR | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP, > + .features[FEAT_1_EDX] = PPRO_FEATURES | CPUID_MTRR | CPUID_CLFLUSH | > + CPUID_MCA | CPUID_PSE36 | CPUID_VME | CPUID_HT, > + .features[FEAT_1_ECX] = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | > + CPUID_EXT_CX16 | CPUID_EXT_POPCNT, > + .features[FEAT_8000_0001_EDX] = > + (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | CPUID_EXT2_LM | > + CPUID_EXT2_SYSCALL | CPUID_EXT2_NX | CPUID_EXT2_3DNOW | > + CPUID_EXT2_3DNOWEXT | CPUID_EXT2_MMXEXT | CPUID_EXT2_FFXSR | > + CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP, > /* Missing: CPUID_EXT3_CMP_LEG, CPUID_EXT3_EXTAPIC, > CPUID_EXT3_CR8LEG, > CPUID_EXT3_MISALIGNSSE, CPUID_EXT3_3DNOWPREFETCH, > CPUID_EXT3_OSVW, CPUID_EXT3_IBS */ > - .ext3_features = CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM | > + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM | > CPUID_EXT3_ABM | CPUID_EXT3_SSE4A, > - .svm_features = CPUID_SVM_NPT | CPUID_SVM_LBRV, > + .features[FEAT_SVM] = CPUID_SVM_NPT | CPUID_SVM_LBRV, > .xlevel = 0x8000001A, > .model_id = "AMD Phenom(tm) 9550 Quad-Core Processor" > }, > @@ -459,15 +453,16 @@ static x86_def_t builtin_x86_defs[] = { > .family = 6, > .model = 15, > .stepping = 11, > - .features = PPRO_FEATURES | > - CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | > - CPUID_PSE36 | CPUID_VME | CPUID_DTS | CPUID_ACPI | CPUID_SS | > - CPUID_HT | CPUID_TM | CPUID_PBE, > - .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_SSSE3 | > - CPUID_EXT_DTES64 | CPUID_EXT_DSCPL | CPUID_EXT_VMX | CPUID_EXT_EST | > - CPUID_EXT_TM2 | CPUID_EXT_CX16 | CPUID_EXT_XTPR | CPUID_EXT_PDCM, > - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX, > - .ext3_features = CPUID_EXT3_LAHF_LM, > + .features[FEAT_1_EDX] = PPRO_FEATURES | CPUID_MTRR | CPUID_CLFLUSH | > + CPUID_MCA | CPUID_PSE36 | CPUID_VME | CPUID_DTS | CPUID_ACPI | > + CPUID_SS | CPUID_HT | CPUID_TM | CPUID_PBE, > + .features[FEAT_1_ECX] = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | > + CPUID_EXT_SSSE3 | CPUID_EXT_DTES64 | CPUID_EXT_DSCPL | > + CPUID_EXT_VMX | CPUID_EXT_EST | CPUID_EXT_TM2 | CPUID_EXT_CX16 | > + CPUID_EXT_XTPR | CPUID_EXT_PDCM, > + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | > + CPUID_EXT2_NX, > + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM, > .xlevel = 0x80000008, > .model_id = "Intel(R) Core(TM)2 Duo CPU T7700 @ 2.40GHz", > }, > @@ -481,19 +476,19 @@ static x86_def_t builtin_x86_defs[] = { > .model = 6, > .stepping = 1, > /* Missing: CPUID_VME, CPUID_HT */ > - .features = PPRO_FEATURES | > - CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | > - CPUID_PSE36, > + .features[FEAT_1_EDX] = PPRO_FEATURES | CPUID_MTRR | CPUID_CLFLUSH | > + CPUID_MCA | CPUID_PSE36, > /* Missing: CPUID_EXT_POPCNT, CPUID_EXT_MONITOR */ > - .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_CX16, > + .features[FEAT_1_ECX] = CPUID_EXT_SSE3 | CPUID_EXT_CX16, > /* Missing: CPUID_EXT2_PDPE1GB, CPUID_EXT2_RDTSCP */ > - .ext2_features = (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | > - CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX, > + .features[FEAT_8000_0001_EDX] = > + (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | CPUID_EXT2_LM | > + CPUID_EXT2_SYSCALL | CPUID_EXT2_NX, > /* Missing: CPUID_EXT3_LAHF_LM, CPUID_EXT3_CMP_LEG, CPUID_EXT3_EXTAPIC, > CPUID_EXT3_CR8LEG, CPUID_EXT3_ABM, CPUID_EXT3_SSE4A, > CPUID_EXT3_MISALIGNSSE, CPUID_EXT3_3DNOWPREFETCH, > CPUID_EXT3_OSVW, CPUID_EXT3_IBS, CPUID_EXT3_SVM */ > - .ext3_features = 0, > + .features[FEAT_8000_0001_ECX] = 0, > .xlevel = 0x80000008, > .model_id = "Common KVM processor" > }, > @@ -506,8 +501,8 @@ static x86_def_t builtin_x86_defs[] = { > .family = 6, > .model = 3, > .stepping = 3, > - .features = PPRO_FEATURES, > - .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_POPCNT, > + .features[FEAT_1_EDX] = PPRO_FEATURES, > + .features[FEAT_1_ECX] = CPUID_EXT_SSE3 | CPUID_EXT_POPCNT, > .xlevel = 0x80000004, > }, > { > @@ -519,11 +514,11 @@ static x86_def_t builtin_x86_defs[] = { > .family = 15, > .model = 6, > .stepping = 1, > - .features = PPRO_FEATURES | > - CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_PSE36, > - .ext_features = CPUID_EXT_SSE3, > - .ext2_features = PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES, > - .ext3_features = 0, > + .features[FEAT_1_EDX] = PPRO_FEATURES | CPUID_MTRR | CPUID_CLFLUSH | > + CPUID_MCA | CPUID_PSE36, > + .features[FEAT_1_ECX] = CPUID_EXT_SSE3, > + .features[FEAT_8000_0001_EDX] = PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES, > + .features[FEAT_8000_0001_ECX] = 0, > .xlevel = 0x80000008, > .model_id = "Common 32-bit KVM processor" > }, > @@ -536,12 +531,13 @@ static x86_def_t builtin_x86_defs[] = { > .family = 6, > .model = 14, > .stepping = 8, > - .features = PPRO_FEATURES | CPUID_VME | > - CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_DTS | CPUID_ACPI | > - CPUID_SS | CPUID_HT | CPUID_TM | CPUID_PBE, > - .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_VMX | > - CPUID_EXT_EST | CPUID_EXT_TM2 | CPUID_EXT_XTPR | CPUID_EXT_PDCM, > - .ext2_features = CPUID_EXT2_NX, > + .features[FEAT_1_EDX] = PPRO_FEATURES | CPUID_VME | CPUID_MTRR | > + CPUID_CLFLUSH | CPUID_MCA | CPUID_DTS | CPUID_ACPI | CPUID_SS | > + CPUID_HT | CPUID_TM | CPUID_PBE, > + .features[FEAT_1_ECX] = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | > + CPUID_EXT_VMX | CPUID_EXT_EST | CPUID_EXT_TM2 | CPUID_EXT_XTPR | > + CPUID_EXT_PDCM, > + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_NX, > .xlevel = 0x80000008, > .model_id = "Genuine Intel(R) CPU T2600 @ 2.16GHz", > }, > @@ -554,7 +550,7 @@ static x86_def_t builtin_x86_defs[] = { > .family = 4, > .model = 0, > .stepping = 0, > - .features = I486_FEATURES, > + .features[FEAT_1_EDX] = I486_FEATURES, > .xlevel = 0, > }, > { > @@ -566,7 +562,7 @@ static x86_def_t builtin_x86_defs[] = { > .family = 5, > .model = 4, > .stepping = 3, > - .features = PENTIUM_FEATURES, > + .features[FEAT_1_EDX] = PENTIUM_FEATURES, > .xlevel = 0, > }, > { > @@ -578,7 +574,7 @@ static x86_def_t builtin_x86_defs[] = { > .family = 6, > .model = 5, > .stepping = 2, > - .features = PENTIUM2_FEATURES, > + .features[FEAT_1_EDX] = PENTIUM2_FEATURES, > .xlevel = 0, > }, > { > @@ -590,7 +586,7 @@ static x86_def_t builtin_x86_defs[] = { > .family = 6, > .model = 7, > .stepping = 3, > - .features = PENTIUM3_FEATURES, > + .features[FEAT_1_EDX] = PENTIUM3_FEATURES, > .xlevel = 0, > }, > { > @@ -602,10 +598,11 @@ static x86_def_t builtin_x86_defs[] = { > .family = 6, > .model = 2, > .stepping = 3, > - .features = PPRO_FEATURES | CPUID_PSE36 | CPUID_VME | CPUID_MTRR | > - CPUID_MCA, > - .ext2_features = (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | > - CPUID_EXT2_MMXEXT | CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT, > + .features[FEAT_1_EDX] = PPRO_FEATURES | CPUID_PSE36 | CPUID_VME | > + CPUID_MTRR | CPUID_MCA, > + .features[FEAT_8000_0001_EDX] = > + (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | CPUID_EXT2_MMXEXT | > + CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT, > .xlevel = 0x80000008, > }, > { > @@ -618,15 +615,16 @@ static x86_def_t builtin_x86_defs[] = { > .family = 6, > .model = 28, > .stepping = 2, > - .features = PPRO_FEATURES | > - CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_VME | CPUID_DTS | > - CPUID_ACPI | CPUID_SS | CPUID_HT | CPUID_TM | CPUID_PBE, > + .features[FEAT_1_EDX] = PPRO_FEATURES | CPUID_MTRR | CPUID_CLFLUSH | > + CPUID_MCA | CPUID_VME | CPUID_DTS | CPUID_ACPI | CPUID_SS | > + CPUID_HT | CPUID_TM | CPUID_PBE, > /* Some CPUs got no CPUID_SEP */ > - .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_SSSE3 | > - CPUID_EXT_DSCPL | CPUID_EXT_EST | CPUID_EXT_TM2 | CPUID_EXT_XTPR, > - .ext2_features = (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | > - CPUID_EXT2_NX, > - .ext3_features = CPUID_EXT3_LAHF_LM, > + .features[FEAT_1_ECX] = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | > + CPUID_EXT_SSSE3 | CPUID_EXT_DSCPL | CPUID_EXT_EST | CPUID_EXT_TM2 | > + CPUID_EXT_XTPR, > + .features[FEAT_8000_0001_EDX] = > + (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | CPUID_EXT2_NX, > + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM, > .xlevel = 0x8000000A, > .model_id = "Intel(R) Atom(TM) CPU N270 @ 1.60GHz", > }, > @@ -639,14 +637,15 @@ static x86_def_t builtin_x86_defs[] = { > .family = 6, > .model = 2, > .stepping = 3, > - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | > - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | > - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | > - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | > - CPUID_DE | CPUID_FP87, > - .ext_features = CPUID_EXT_SSSE3 | CPUID_EXT_SSE3, > - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL, > - .ext3_features = CPUID_EXT3_LAHF_LM, > + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | > + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | > + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | > + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | > + CPUID_PSE | CPUID_DE | CPUID_FP87, > + .features[FEAT_1_ECX] = CPUID_EXT_SSSE3 | CPUID_EXT_SSE3, > + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_NX | > + CPUID_EXT2_SYSCALL, > + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM, > .xlevel = 0x8000000A, > .model_id = "Intel Celeron_4x0 (Conroe/Merom Class Core 2)", > }, > @@ -659,15 +658,16 @@ static x86_def_t builtin_x86_defs[] = { > .family = 6, > .model = 2, > .stepping = 3, > - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | > - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | > - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | > - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | > - CPUID_DE | CPUID_FP87, > - .ext_features = CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | > - CPUID_EXT_SSE3, > - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL, > - .ext3_features = CPUID_EXT3_LAHF_LM, > + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | > + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | > + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | > + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | > + CPUID_PSE | CPUID_DE | CPUID_FP87, > + .features[FEAT_1_ECX] = CPUID_EXT_SSE41 | CPUID_EXT_CX16 | > + CPUID_EXT_SSSE3 | CPUID_EXT_SSE3, > + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_NX | > + CPUID_EXT2_SYSCALL, > + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM, > .xlevel = 0x8000000A, > .model_id = "Intel Core 2 Duo P9xxx (Penryn Class Core 2)", > }, > @@ -680,15 +680,17 @@ static x86_def_t builtin_x86_defs[] = { > .family = 6, > .model = 2, > .stepping = 3, > - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | > - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | > - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | > - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | > - CPUID_DE | CPUID_FP87, > - .ext_features = CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 | > - CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_SSE3, > - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX, > - .ext3_features = CPUID_EXT3_LAHF_LM, > + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | > + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | > + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | > + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | > + CPUID_PSE | CPUID_DE | CPUID_FP87, > + .features[FEAT_1_ECX] = CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | > + CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | > + CPUID_EXT_SSE3, > + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | > + CPUID_EXT2_NX, > + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM, > .xlevel = 0x8000000A, > .model_id = "Intel Core i7 9xx (Nehalem Class Core i7)", > }, > @@ -701,16 +703,17 @@ static x86_def_t builtin_x86_defs[] = { > .family = 6, > .model = 44, > .stepping = 1, > - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | > - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | > - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | > - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | > - CPUID_DE | CPUID_FP87, > - .ext_features = CPUID_EXT_AES | CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | > - CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | > - CPUID_EXT_SSE3, > - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX, > - .ext3_features = CPUID_EXT3_LAHF_LM, > + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | > + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | > + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | > + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | > + CPUID_PSE | CPUID_DE | CPUID_FP87, > + .features[FEAT_1_ECX] = CPUID_EXT_AES | CPUID_EXT_POPCNT | > + CPUID_EXT_SSE42 | CPUID_EXT_SSE41 | CPUID_EXT_CX16 | > + CPUID_EXT_SSSE3 | CPUID_EXT_SSE3, > + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | > + CPUID_EXT2_NX, > + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM, > .xlevel = 0x8000000A, > .model_id = "Westmere E56xx/L56xx/X56xx (Nehalem-C)", > }, > @@ -723,19 +726,19 @@ static x86_def_t builtin_x86_defs[] = { > .family = 6, > .model = 42, > .stepping = 1, > - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | > - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | > - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | > - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | > - CPUID_DE | CPUID_FP87, > - .ext_features = CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES | > - CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_POPCNT | > - CPUID_EXT_X2APIC | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 | > - CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ | > - CPUID_EXT_SSE3, > - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX | > - CPUID_EXT2_SYSCALL, > - .ext3_features = CPUID_EXT3_LAHF_LM, > + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | > + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | > + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | > + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | > + CPUID_PSE | CPUID_DE | CPUID_FP87, > + .features[FEAT_1_ECX] = CPUID_EXT_AVX | CPUID_EXT_XSAVE | > + CPUID_EXT_AES | CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_POPCNT | > + CPUID_EXT_X2APIC | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 | > + CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ | > + CPUID_EXT_SSE3, > + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | > + CPUID_EXT2_NX | CPUID_EXT2_SYSCALL, > + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM, > .xlevel = 0x8000000A, > .model_id = "Intel Xeon E312xx (Sandy Bridge)", > }, > @@ -748,21 +751,21 @@ static x86_def_t builtin_x86_defs[] = { > .family = 6, > .model = 60, > .stepping = 1, > - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | > - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | > - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | > - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | > - CPUID_DE | CPUID_FP87, > - .ext_features = CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES | > - CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 | > - CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | > - CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 | > - CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE | > - CPUID_EXT_PCID, > - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX | > - CPUID_EXT2_SYSCALL, > - .ext3_features = CPUID_EXT3_LAHF_LM, > - .cpuid_7_0_ebx_features = CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | > + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | > + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | > + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | > + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | > + CPUID_PSE | CPUID_DE | CPUID_FP87, > + .features[FEAT_1_ECX] = CPUID_EXT_AVX | CPUID_EXT_XSAVE | > + CPUID_EXT_AES | CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | > + CPUID_EXT_SSE42 | CPUID_EXT_SSE41 | CPUID_EXT_CX16 | > + CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 | > + CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE | > + CPUID_EXT_PCID, > + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | > + CPUID_EXT2_NX | CPUID_EXT2_SYSCALL, > + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM, > + .features[FEAT_7_0_EBX] = CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | > CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP | > CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID | > CPUID_7_0_EBX_RTM, > @@ -778,18 +781,18 @@ static x86_def_t builtin_x86_defs[] = { > .family = 15, > .model = 6, > .stepping = 1, > - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | > - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | > - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | > - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | > - CPUID_DE | CPUID_FP87, > - .ext_features = CPUID_EXT_SSE3, > - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_FXSR | CPUID_EXT2_MMX | > - CPUID_EXT2_NX | CPUID_EXT2_PSE36 | CPUID_EXT2_PAT | > + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | > + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | > + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | > + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | > + CPUID_PSE | CPUID_DE | CPUID_FP87, > + .features[FEAT_1_ECX] = CPUID_EXT_SSE3, > + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_FXSR | > + CPUID_EXT2_MMX | CPUID_EXT2_NX | CPUID_EXT2_PSE36 | CPUID_EXT2_PAT | > CPUID_EXT2_CMOV | CPUID_EXT2_MCA | CPUID_EXT2_PGE | > - CPUID_EXT2_MTRR | CPUID_EXT2_SYSCALL | CPUID_EXT2_APIC | > - CPUID_EXT2_CX8 | CPUID_EXT2_MCE | CPUID_EXT2_PAE | CPUID_EXT2_MSR | > - CPUID_EXT2_TSC | CPUID_EXT2_PSE | CPUID_EXT2_DE | CPUID_EXT2_FPU, > + CPUID_EXT2_MTRR | CPUID_EXT2_SYSCALL | CPUID_EXT2_APIC | > + CPUID_EXT2_CX8 | CPUID_EXT2_MCE | CPUID_EXT2_PAE | CPUID_EXT2_MSR | > + CPUID_EXT2_TSC | CPUID_EXT2_PSE | CPUID_EXT2_DE | CPUID_EXT2_FPU, > .xlevel = 0x80000008, > .model_id = "AMD Opteron 240 (Gen 1 Class Opteron)", > }, > @@ -802,20 +805,20 @@ static x86_def_t builtin_x86_defs[] = { > .family = 15, > .model = 6, > .stepping = 1, > - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | > - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | > - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | > - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | > - CPUID_DE | CPUID_FP87, > - .ext_features = CPUID_EXT_CX16 | CPUID_EXT_SSE3, > - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_FXSR | > - CPUID_EXT2_MMX | CPUID_EXT2_NX | CPUID_EXT2_PSE36 | > - CPUID_EXT2_PAT | CPUID_EXT2_CMOV | CPUID_EXT2_MCA | > - CPUID_EXT2_PGE | CPUID_EXT2_MTRR | CPUID_EXT2_SYSCALL | > - CPUID_EXT2_APIC | CPUID_EXT2_CX8 | CPUID_EXT2_MCE | > - CPUID_EXT2_PAE | CPUID_EXT2_MSR | CPUID_EXT2_TSC | CPUID_EXT2_PSE | > - CPUID_EXT2_DE | CPUID_EXT2_FPU, > - .ext3_features = CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM, > + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | > + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | > + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | > + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | > + CPUID_PSE | CPUID_DE | CPUID_FP87, > + .features[FEAT_1_ECX] = CPUID_EXT_CX16 | CPUID_EXT_SSE3, > + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | > + CPUID_EXT2_FXSR | CPUID_EXT2_MMX | CPUID_EXT2_NX | > + CPUID_EXT2_PSE36 | CPUID_EXT2_PAT | CPUID_EXT2_CMOV | > + CPUID_EXT2_MCA | CPUID_EXT2_PGE | CPUID_EXT2_MTRR | > + CPUID_EXT2_SYSCALL | CPUID_EXT2_APIC | CPUID_EXT2_CX8 | > + CPUID_EXT2_MCE | CPUID_EXT2_PAE | CPUID_EXT2_MSR | CPUID_EXT2_TSC | > + CPUID_EXT2_PSE | CPUID_EXT2_DE | CPUID_EXT2_FPU, > + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM, > .xlevel = 0x80000008, > .model_id = "AMD Opteron 22xx (Gen 2 Class Opteron)", > }, > @@ -828,22 +831,23 @@ static x86_def_t builtin_x86_defs[] = { > .family = 15, > .model = 6, > .stepping = 1, > - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | > - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | > - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | > - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | > - CPUID_DE | CPUID_FP87, > - .ext_features = CPUID_EXT_POPCNT | CPUID_EXT_CX16 | CPUID_EXT_MONITOR | > - CPUID_EXT_SSE3, > - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_FXSR | > - CPUID_EXT2_MMX | CPUID_EXT2_NX | CPUID_EXT2_PSE36 | > - CPUID_EXT2_PAT | CPUID_EXT2_CMOV | CPUID_EXT2_MCA | > - CPUID_EXT2_PGE | CPUID_EXT2_MTRR | CPUID_EXT2_SYSCALL | > - CPUID_EXT2_APIC | CPUID_EXT2_CX8 | CPUID_EXT2_MCE | > - CPUID_EXT2_PAE | CPUID_EXT2_MSR | CPUID_EXT2_TSC | CPUID_EXT2_PSE | > - CPUID_EXT2_DE | CPUID_EXT2_FPU, > - .ext3_features = CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | > - CPUID_EXT3_ABM | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM, > + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | > + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | > + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | > + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | > + CPUID_PSE | CPUID_DE | CPUID_FP87, > + .features[FEAT_1_ECX] = CPUID_EXT_POPCNT | CPUID_EXT_CX16 | > + CPUID_EXT_MONITOR | CPUID_EXT_SSE3, > + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | > + CPUID_EXT2_FXSR | CPUID_EXT2_MMX | CPUID_EXT2_NX | > + CPUID_EXT2_PSE36 | CPUID_EXT2_PAT | CPUID_EXT2_CMOV | > + CPUID_EXT2_MCA | CPUID_EXT2_PGE | CPUID_EXT2_MTRR | > + CPUID_EXT2_SYSCALL | CPUID_EXT2_APIC | CPUID_EXT2_CX8 | > + CPUID_EXT2_MCE | CPUID_EXT2_PAE | CPUID_EXT2_MSR | CPUID_EXT2_TSC | > + CPUID_EXT2_PSE | CPUID_EXT2_DE | CPUID_EXT2_FPU, > + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_MISALIGNSSE | > + CPUID_EXT3_SSE4A | CPUID_EXT3_ABM | CPUID_EXT3_SVM | > + CPUID_EXT3_LAHF_LM, > .xlevel = 0x80000008, > .model_id = "AMD Opteron 23xx (Gen 3 Class Opteron)", > }, > @@ -856,26 +860,26 @@ static x86_def_t builtin_x86_defs[] = { > .family = 21, > .model = 1, > .stepping = 2, > - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | > - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | > - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | > - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | > - CPUID_DE | CPUID_FP87, > - .ext_features = CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES | > - CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 | > - CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ | > - CPUID_EXT_SSE3, > - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | > - CPUID_EXT2_PDPE1GB | CPUID_EXT2_FXSR | CPUID_EXT2_MMX | > - CPUID_EXT2_NX | CPUID_EXT2_PSE36 | CPUID_EXT2_PAT | > - CPUID_EXT2_CMOV | CPUID_EXT2_MCA | CPUID_EXT2_PGE | > - CPUID_EXT2_MTRR | CPUID_EXT2_SYSCALL | CPUID_EXT2_APIC | > - CPUID_EXT2_CX8 | CPUID_EXT2_MCE | CPUID_EXT2_PAE | CPUID_EXT2_MSR | > - CPUID_EXT2_TSC | CPUID_EXT2_PSE | CPUID_EXT2_DE | CPUID_EXT2_FPU, > - .ext3_features = CPUID_EXT3_FMA4 | CPUID_EXT3_XOP | > - CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_MISALIGNSSE | > - CPUID_EXT3_SSE4A | CPUID_EXT3_ABM | CPUID_EXT3_SVM | > - CPUID_EXT3_LAHF_LM, > + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | > + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | > + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | > + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | > + CPUID_PSE | CPUID_DE | CPUID_FP87, > + .features[FEAT_1_ECX] = CPUID_EXT_AVX | CPUID_EXT_XSAVE | > + CPUID_EXT_AES | CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | > + CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | > + CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3, > + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | > + CPUID_EXT2_PDPE1GB | CPUID_EXT2_FXSR | CPUID_EXT2_MMX | > + CPUID_EXT2_NX | CPUID_EXT2_PSE36 | CPUID_EXT2_PAT | > + CPUID_EXT2_CMOV | CPUID_EXT2_MCA | CPUID_EXT2_PGE | > + CPUID_EXT2_MTRR | CPUID_EXT2_SYSCALL | CPUID_EXT2_APIC | > + CPUID_EXT2_CX8 | CPUID_EXT2_MCE | CPUID_EXT2_PAE | CPUID_EXT2_MSR | > + CPUID_EXT2_TSC | CPUID_EXT2_PSE | CPUID_EXT2_DE | CPUID_EXT2_FPU, > + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_FMA4 | CPUID_EXT3_XOP | > + CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_MISALIGNSSE | > + CPUID_EXT3_SSE4A | CPUID_EXT3_ABM | CPUID_EXT3_SVM | > + CPUID_EXT3_LAHF_LM, > .xlevel = 0x8000001A, > .model_id = "AMD Opteron 62xx class CPU", > }, > @@ -888,26 +892,26 @@ static x86_def_t builtin_x86_defs[] = { > .family = 21, > .model = 2, > .stepping = 0, > - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | > - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | > - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | > - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | > - CPUID_DE | CPUID_FP87, > - .ext_features = CPUID_EXT_F16C | CPUID_EXT_AVX | CPUID_EXT_XSAVE | > - CPUID_EXT_AES | CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | > - CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_FMA | > + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | > + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | > + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | > + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | > + CPUID_PSE | CPUID_DE | CPUID_FP87, > + .features[FEAT_1_ECX] = CPUID_EXT_F16C | CPUID_EXT_AVX | > + CPUID_EXT_XSAVE | CPUID_EXT_AES | CPUID_EXT_POPCNT | > + CPUID_EXT_SSE42 | CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_FMA | > CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3, > - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | > - CPUID_EXT2_PDPE1GB | CPUID_EXT2_FXSR | CPUID_EXT2_MMX | > - CPUID_EXT2_NX | CPUID_EXT2_PSE36 | CPUID_EXT2_PAT | > - CPUID_EXT2_CMOV | CPUID_EXT2_MCA | CPUID_EXT2_PGE | > - CPUID_EXT2_MTRR | CPUID_EXT2_SYSCALL | CPUID_EXT2_APIC | > - CPUID_EXT2_CX8 | CPUID_EXT2_MCE | CPUID_EXT2_PAE | CPUID_EXT2_MSR | > - CPUID_EXT2_TSC | CPUID_EXT2_PSE | CPUID_EXT2_DE | CPUID_EXT2_FPU, > - .ext3_features = CPUID_EXT3_TBM | CPUID_EXT3_FMA4 | CPUID_EXT3_XOP | > - CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_MISALIGNSSE | > + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | > + CPUID_EXT2_PDPE1GB | CPUID_EXT2_FXSR | CPUID_EXT2_MMX | > + CPUID_EXT2_NX | CPUID_EXT2_PSE36 | CPUID_EXT2_PAT | > + CPUID_EXT2_CMOV | CPUID_EXT2_MCA | CPUID_EXT2_PGE | > + CPUID_EXT2_MTRR | CPUID_EXT2_SYSCALL | CPUID_EXT2_APIC | > + CPUID_EXT2_CX8 | CPUID_EXT2_MCE | CPUID_EXT2_PAE | CPUID_EXT2_MSR | > + CPUID_EXT2_TSC | CPUID_EXT2_PSE | CPUID_EXT2_DE | CPUID_EXT2_FPU, > + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_TBM | CPUID_EXT3_FMA4 | > + CPUID_EXT3_XOP | CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_MISALIGNSSE | > CPUID_EXT3_SSE4A | CPUID_EXT3_ABM | CPUID_EXT3_SVM | > - CPUID_EXT3_LAHF_LM, > + CPUID_EXT3_LAHF_LM, > .xlevel = 0x8000001A, > .model_id = "AMD Opteron 63xx class CPU", > }, > @@ -955,20 +959,22 @@ static void kvm_cpu_fill_host(x86_def_t *x86_cpu_def) > x86_cpu_def->stepping = eax & 0x0F; > > x86_cpu_def->level = kvm_arch_get_supported_cpuid(s, 0x0, 0, R_EAX); > - x86_cpu_def->features = kvm_arch_get_supported_cpuid(s, 0x1, 0, R_EDX); > - x86_cpu_def->ext_features = kvm_arch_get_supported_cpuid(s, 0x1, 0, R_ECX); > + x86_cpu_def->features[FEAT_1_EDX] = > + kvm_arch_get_supported_cpuid(s, 0x1, 0, R_EDX); > + x86_cpu_def->features[FEAT_1_ECX] = > + kvm_arch_get_supported_cpuid(s, 0x1, 0, R_ECX); > > if (x86_cpu_def->level >= 7) { > - x86_cpu_def->cpuid_7_0_ebx_features = > + x86_cpu_def->features[FEAT_7_0_EBX] = > kvm_arch_get_supported_cpuid(s, 0x7, 0, R_EBX); > } else { > - x86_cpu_def->cpuid_7_0_ebx_features = 0; > + x86_cpu_def->features[FEAT_7_0_EBX] = 0; > } > > x86_cpu_def->xlevel = kvm_arch_get_supported_cpuid(s, 0x80000000, 0, R_EAX); > - x86_cpu_def->ext2_features = > + x86_cpu_def->features[FEAT_8000_0001_EDX] = > kvm_arch_get_supported_cpuid(s, 0x80000001, 0, R_EDX); > - x86_cpu_def->ext3_features = > + x86_cpu_def->features[FEAT_8000_0001_ECX] = > kvm_arch_get_supported_cpuid(s, 0x80000001, 0, R_ECX); > > cpu_x86_fill_model_id(x86_cpu_def->model_id); > @@ -984,15 +990,15 @@ static void kvm_cpu_fill_host(x86_def_t *x86_cpu_def) > /* Support VIA max extended level */ > x86_cpu_def->xlevel2 = eax; > host_cpuid(0xC0000001, 0, &eax, &ebx, &ecx, &edx); > - x86_cpu_def->ext4_features = > + x86_cpu_def->features[FEAT_C000_0001_EDX] = > kvm_arch_get_supported_cpuid(s, 0xC0000001, 0, R_EDX); > } > } > > /* Other KVM-specific feature fields: */ > - x86_cpu_def->svm_features = > + x86_cpu_def->features[FEAT_SVM] = > kvm_arch_get_supported_cpuid(s, 0x8000000A, 0, R_EDX); > - x86_cpu_def->kvm_features = > + x86_cpu_def->features[FEAT_KVM] = > kvm_arch_get_supported_cpuid(s, KVM_CPUID_FEATURES, 0, R_EAX); > > #endif /* CONFIG_KVM */ > @@ -1028,21 +1034,29 @@ static int kvm_check_features_against_host(x86_def_t *guest_def) > uint32_t mask; > int rv, i; > struct model_features_t ft[] = { > - {&guest_def->features, &host_def.features, > + {&guest_def->features[FEAT_1_EDX], > + &host_def.features[FEAT_1_EDX], > FEAT_1_EDX }, > - {&guest_def->ext_features, &host_def.ext_features, > + {&guest_def->features[FEAT_1_ECX], > + &host_def.features[FEAT_1_ECX], > FEAT_1_ECX }, > - {&guest_def->ext2_features, &host_def.ext2_features, > + {&guest_def->features[FEAT_8000_0001_EDX], > + &host_def.features[FEAT_8000_0001_EDX], > FEAT_8000_0001_EDX }, > - {&guest_def->ext3_features, &host_def.ext3_features, > + {&guest_def->features[FEAT_8000_0001_ECX], > + &host_def.features[FEAT_8000_0001_ECX], > FEAT_8000_0001_ECX }, > - {&guest_def->ext4_features, &host_def.ext4_features, > + {&guest_def->features[FEAT_C000_0001_EDX], > + &host_def.features[FEAT_C000_0001_EDX], > FEAT_C000_0001_EDX }, > - {&guest_def->cpuid_7_0_ebx_features, &host_def.cpuid_7_0_ebx_features, > + {&guest_def->features[FEAT_7_0_EBX], > + &host_def.features[FEAT_7_0_EBX], > FEAT_7_0_EBX }, > - {&guest_def->svm_features, &host_def.svm_features, > + {&guest_def->features[FEAT_SVM], > + &host_def.features[FEAT_SVM], > FEAT_SVM }, > - {&guest_def->kvm_features, &host_def.kvm_features, > + {&guest_def->features[FEAT_KVM], > + &host_def.features[FEAT_KVM], > FEAT_KVM }, > }; > > @@ -1459,22 +1473,28 @@ static int cpu_x86_parse_featurestr(x86_def_t *x86_cpu_def, char *features) > } > featurestr = strtok(NULL, ","); > } > - x86_cpu_def->features |= plus_features[FEAT_1_EDX]; > - x86_cpu_def->ext_features |= plus_features[FEAT_1_ECX]; > - x86_cpu_def->ext2_features |= plus_features[FEAT_8000_0001_EDX]; > - x86_cpu_def->ext3_features |= plus_features[FEAT_8000_0001_ECX]; > - x86_cpu_def->ext4_features |= plus_features[FEAT_C000_0001_EDX]; > - x86_cpu_def->kvm_features |= plus_features[FEAT_KVM]; > - x86_cpu_def->svm_features |= plus_features[FEAT_SVM]; > - x86_cpu_def->cpuid_7_0_ebx_features |= plus_features[FEAT_7_0_EBX]; > - x86_cpu_def->features &= ~minus_features[FEAT_1_EDX]; > - x86_cpu_def->ext_features &= ~minus_features[FEAT_1_ECX]; > - x86_cpu_def->ext2_features &= ~minus_features[FEAT_8000_0001_EDX]; > - x86_cpu_def->ext3_features &= ~minus_features[FEAT_8000_0001_ECX]; > - x86_cpu_def->ext4_features &= ~minus_features[FEAT_C000_0001_EDX]; > - x86_cpu_def->kvm_features &= ~minus_features[FEAT_KVM]; > - x86_cpu_def->svm_features &= ~minus_features[FEAT_SVM]; > - x86_cpu_def->cpuid_7_0_ebx_features &= ~minus_features[FEAT_7_0_EBX]; > + x86_cpu_def->features[FEAT_1_EDX] |= plus_features[FEAT_1_EDX]; > + x86_cpu_def->features[FEAT_1_ECX] |= plus_features[FEAT_1_ECX]; > + x86_cpu_def->features[FEAT_8000_0001_EDX] |= > + plus_features[FEAT_8000_0001_EDX]; > + x86_cpu_def->features[FEAT_8000_0001_ECX] |= > + plus_features[FEAT_8000_0001_ECX]; > + x86_cpu_def->features[FEAT_C000_0001_EDX] |= > + plus_features[FEAT_C000_0001_EDX]; > + x86_cpu_def->features[FEAT_KVM] |= plus_features[FEAT_KVM]; > + x86_cpu_def->features[FEAT_SVM] |= plus_features[FEAT_SVM]; > + x86_cpu_def->features[FEAT_7_0_EBX] |= plus_features[FEAT_7_0_EBX]; > + x86_cpu_def->features[FEAT_1_EDX] &= ~minus_features[FEAT_1_EDX]; > + x86_cpu_def->features[FEAT_1_ECX] &= ~minus_features[FEAT_1_ECX]; > + x86_cpu_def->features[FEAT_8000_0001_EDX] &= > + ~minus_features[FEAT_8000_0001_EDX]; > + x86_cpu_def->features[FEAT_8000_0001_ECX] &= > + ~minus_features[FEAT_8000_0001_ECX]; > + x86_cpu_def->features[FEAT_C000_0001_EDX] &= > + ~minus_features[FEAT_C000_0001_EDX]; > + x86_cpu_def->features[FEAT_KVM] &= ~minus_features[FEAT_KVM]; > + x86_cpu_def->features[FEAT_SVM] &= ~minus_features[FEAT_SVM]; > + x86_cpu_def->features[FEAT_7_0_EBX] &= ~minus_features[FEAT_7_0_EBX]; > if (check_cpuid && kvm_enabled()) { > if (kvm_check_features_against_host(x86_cpu_def) && enforce_cpuid) > goto error; > @@ -1566,21 +1586,21 @@ static void filter_features_for_kvm(X86CPU *cpu) > CPUX86State *env = &cpu->env; > KVMState *s = kvm_state; > > - env->cpuid_features &= > + env->features[FEAT_1_EDX] &= > kvm_arch_get_supported_cpuid(s, 1, 0, R_EDX); > - env->cpuid_ext_features &= > + env->features[FEAT_1_ECX] &= > kvm_arch_get_supported_cpuid(s, 1, 0, R_ECX); > - env->cpuid_ext2_features &= > + env->features[FEAT_8000_0001_EDX] &= > kvm_arch_get_supported_cpuid(s, 0x80000001, 0, R_EDX); > - env->cpuid_ext3_features &= > + env->features[FEAT_8000_0001_ECX] &= > kvm_arch_get_supported_cpuid(s, 0x80000001, 0, R_ECX); > - env->cpuid_svm_features &= > + env->features[FEAT_SVM] &= > kvm_arch_get_supported_cpuid(s, 0x8000000A, 0, R_EDX); > - env->cpuid_7_0_ebx_features &= > + env->features[FEAT_7_0_EBX] &= > kvm_arch_get_supported_cpuid(s, 7, 0, R_EBX); > - env->cpuid_kvm_features &= > + env->features[FEAT_KVM] &= > kvm_arch_get_supported_cpuid(s, KVM_CPUID_FEATURES, 0, R_EAX); > - env->cpuid_ext4_features &= > + env->features[FEAT_C000_0001_EDX] &= > kvm_arch_get_supported_cpuid(s, 0xC0000001, 0, R_EDX); > > } > @@ -1619,15 +1639,15 @@ int cpu_x86_register(X86CPU *cpu, const char *cpu_model) > object_property_set_int(OBJECT(cpu), def->family, "family", &error); > object_property_set_int(OBJECT(cpu), def->model, "model", &error); > object_property_set_int(OBJECT(cpu), def->stepping, "stepping", &error); > - env->cpuid_features = def->features; > - env->cpuid_ext_features = def->ext_features; > - env->cpuid_ext2_features = def->ext2_features; > - env->cpuid_ext3_features = def->ext3_features; > + env->features[FEAT_1_EDX] = def->features[FEAT_1_EDX]; > + env->features[FEAT_1_ECX] = def->features[FEAT_1_ECX]; > + env->features[FEAT_8000_0001_EDX] = def->features[FEAT_8000_0001_EDX]; > + env->features[FEAT_8000_0001_ECX] = def->features[FEAT_8000_0001_ECX]; > object_property_set_int(OBJECT(cpu), def->xlevel, "xlevel", &error); > - env->cpuid_kvm_features = def->kvm_features; > - env->cpuid_svm_features = def->svm_features; > - env->cpuid_ext4_features = def->ext4_features; > - env->cpuid_7_0_ebx_features = def->cpuid_7_0_ebx_features; > + env->features[FEAT_KVM] = def->features[FEAT_KVM]; > + env->features[FEAT_SVM] = def->features[FEAT_SVM]; > + env->features[FEAT_C000_0001_EDX] = def->features[FEAT_C000_0001_EDX]; > + env->features[FEAT_7_0_EBX] = def->features[FEAT_7_0_EBX]; > env->cpuid_xlevel2 = def->xlevel2; > object_property_set_int(OBJECT(cpu), (int64_t)def->tsc_khz * 1000, > "tsc-frequency", &error); > @@ -1650,7 +1670,7 @@ error: > > void cpu_clear_apic_feature(CPUX86State *env) > { > - env->cpuid_features &= ~CPUID_APIC; > + env->features[FEAT_1_EDX] &= ~CPUID_APIC; > } > > #endif /* !CONFIG_USER_ONLY */ > @@ -1738,8 +1758,8 @@ void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count, > case 1: > *eax = env->cpuid_version; > *ebx = (env->cpuid_apic_id << 24) | 8 << 8; /* CLFLUSH size in quad words, Linux wants it. */ > - *ecx = env->cpuid_ext_features; > - *edx = env->cpuid_features; > + *ecx = env->features[FEAT_1_ECX]; > + *edx = env->features[FEAT_1_EDX]; > if (cs->nr_cores * cs->nr_threads > 1) { > *ebx |= (cs->nr_cores * cs->nr_threads) << 16; > *edx |= 1 << 28; /* HTT bit */ > @@ -1807,7 +1827,7 @@ void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count, > /* Structured Extended Feature Flags Enumeration Leaf */ > if (count == 0) { > *eax = 0; /* Maximum ECX value for sub-leaves */ > - *ebx = env->cpuid_7_0_ebx_features; /* Feature flags */ > + *ebx = env->features[FEAT_7_0_EBX]; /* Feature flags */ > *ecx = 0; /* Reserved */ > *edx = 0; /* Reserved */ > } else { > @@ -1842,7 +1862,7 @@ void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count, > break; > case 0xD: > /* Processor Extended State */ > - if (!(env->cpuid_ext_features & CPUID_EXT_XSAVE)) { > + if (!(env->features[FEAT_1_ECX] & CPUID_EXT_XSAVE)) { > *eax = 0; > *ebx = 0; > *ecx = 0; > @@ -1872,8 +1892,8 @@ void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count, > case 0x80000001: > *eax = env->cpuid_version; > *ebx = 0; > - *ecx = env->cpuid_ext3_features; > - *edx = env->cpuid_ext2_features; > + *ecx = env->features[FEAT_8000_0001_ECX]; > + *edx = env->features[FEAT_8000_0001_EDX]; > > /* The Linux kernel checks for the CMPLegacy bit and > * discards multiple thread information if it is set. > @@ -1914,12 +1934,12 @@ void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count, > case 0x80000008: > /* virtual & phys address size in low 2 bytes. */ > /* XXX: This value must match the one used in the MMU code. */ > - if (env->cpuid_ext2_features & CPUID_EXT2_LM) { > + if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_LM) { > /* 64 bit processor */ > /* XXX: The physical address space is limited to 42 bits in exec.c. */ > *eax = 0x00003028; /* 48 bits virtual, 40 bits physical */ > } else { > - if (env->cpuid_features & CPUID_PSE36) { > + if (env->features[FEAT_1_EDX] & CPUID_PSE36) { > *eax = 0x00000024; /* 36 bits physical */ > } else { > *eax = 0x00000020; /* 32 bits physical */ > @@ -1933,11 +1953,11 @@ void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count, > } > break; > case 0x8000000A: > - if (env->cpuid_ext3_features & CPUID_EXT3_SVM) { > + if (env->features[FEAT_8000_0001_ECX] & CPUID_EXT3_SVM) { > *eax = 0x00000001; /* SVM Revision */ > *ebx = 0x00000010; /* nr of ASIDs */ > *ecx = 0; > - *edx = env->cpuid_svm_features; /* optional features */ > + *edx = env->features[FEAT_SVM]; /* optional features */ > } else { > *eax = 0; > *ebx = 0; > @@ -1956,7 +1976,7 @@ void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count, > *eax = env->cpuid_version; > *ebx = 0; > *ecx = 0; > - *edx = env->cpuid_ext4_features; > + *edx = env->features[FEAT_C000_0001_EDX]; > break; > case 0xC0000002: > case 0xC0000003: > @@ -2088,7 +2108,7 @@ static void mce_init(X86CPU *cpu) > unsigned int bank; > > if (((cenv->cpuid_version >> 8) & 0xf) >= 6 > - && (cenv->cpuid_features & (CPUID_MCE | CPUID_MCA)) == > + && (cenv->features[FEAT_1_EDX] & (CPUID_MCE | CPUID_MCA)) == > (CPUID_MCE | CPUID_MCA)) { > cenv->mcg_cap = MCE_CAP_DEF | MCE_BANKS_DEF; > cenv->mcg_ctl = ~(uint64_t)0; > @@ -2149,7 +2169,7 @@ void x86_cpu_realize(Object *obj, Error **errp) > X86CPU *cpu = X86_CPU(obj); > CPUX86State *env = &cpu->env; > > - if (env->cpuid_7_0_ebx_features && env->cpuid_level < 7) { > + if (env->features[FEAT_7_0_EBX] && env->cpuid_level < 7) { > env->cpuid_level = 7; > } > > @@ -2159,21 +2179,21 @@ void x86_cpu_realize(Object *obj, Error **errp) > if (env->cpuid_vendor1 == CPUID_VENDOR_AMD_1 && > env->cpuid_vendor2 == CPUID_VENDOR_AMD_2 && > env->cpuid_vendor3 == CPUID_VENDOR_AMD_3) { > - env->cpuid_ext2_features &= ~CPUID_EXT2_AMD_ALIASES; > - env->cpuid_ext2_features |= (env->cpuid_features > + env->features[FEAT_8000_0001_EDX] &= ~CPUID_EXT2_AMD_ALIASES; > + env->features[FEAT_8000_0001_EDX] |= (env->features[FEAT_1_EDX] > & CPUID_EXT2_AMD_ALIASES); > } > > if (!kvm_enabled()) { > - env->cpuid_features &= TCG_FEATURES; > - env->cpuid_ext_features &= TCG_EXT_FEATURES; > - env->cpuid_ext2_features &= (TCG_EXT2_FEATURES > + env->features[FEAT_1_EDX] &= TCG_FEATURES; > + env->features[FEAT_1_ECX] &= TCG_EXT_FEATURES; > + env->features[FEAT_8000_0001_EDX] &= (TCG_EXT2_FEATURES > #ifdef TARGET_X86_64 > | CPUID_EXT2_SYSCALL | CPUID_EXT2_LM > #endif > ); > - env->cpuid_ext3_features &= TCG_EXT3_FEATURES; > - env->cpuid_svm_features &= TCG_SVM_FEATURES; > + env->features[FEAT_8000_0001_ECX] &= TCG_EXT3_FEATURES; > + env->features[FEAT_SVM] &= TCG_SVM_FEATURES; > } else { > #ifdef CONFIG_KVM > filter_features_for_kvm(cpu); > @@ -2183,7 +2203,7 @@ void x86_cpu_realize(Object *obj, Error **errp) > #ifndef CONFIG_USER_ONLY > qemu_register_reset(x86_cpu_machine_reset_cb, cpu); > > - if (cpu->env.cpuid_features & CPUID_APIC || smp_cpus > 1) { > + if (cpu->env.features[FEAT_1_EDX] & CPUID_APIC || smp_cpus > 1) { > x86_cpu_apic_init(cpu, errp); > if (error_is_set(errp)) { > return; > diff --git a/target-i386/cpu.h b/target-i386/cpu.h > index e4a7c50..b202427 100644 > --- a/target-i386/cpu.h > +++ b/target-i386/cpu.h > @@ -817,24 +817,15 @@ typedef struct CPUX86State { > uint64_t pat; > > /* processor features (e.g. for CPUID insn) */ > - uint32_t cpuid_level; > + uint32_t cpuid_level, cpuid_xlevel, cpuid_xlevel2; > + FeatureWordArray features; > uint32_t cpuid_vendor1; > uint32_t cpuid_vendor2; > uint32_t cpuid_vendor3; > uint32_t cpuid_version; > - uint32_t cpuid_features; > - uint32_t cpuid_ext_features; > - uint32_t cpuid_xlevel; > uint32_t cpuid_model[12]; > - uint32_t cpuid_ext2_features; > - uint32_t cpuid_ext3_features; > uint32_t cpuid_apic_id; > int cpuid_vendor_override; > - /* Store the results of Centaur's CPUID instructions */ > - uint32_t cpuid_xlevel2; > - uint32_t cpuid_ext4_features; > - /* Flags from CPUID[EAX=7,ECX=0].EBX */ > - uint32_t cpuid_7_0_ebx_features; > > /* MTRRs */ > uint64_t mtrr_fixed[11]; > @@ -848,8 +839,6 @@ typedef struct CPUX86State { > uint8_t soft_interrupt; > uint8_t has_error_code; > uint32_t sipi_vector; > - uint32_t cpuid_kvm_features; > - uint32_t cpuid_svm_features; > bool tsc_valid; > int tsc_khz; > void *kvm_xsave_buf; > diff --git a/target-i386/helper.c b/target-i386/helper.c > index fa622e1..99da02e 100644 > --- a/target-i386/helper.c > +++ b/target-i386/helper.c > @@ -449,7 +449,7 @@ void cpu_x86_update_cr4(CPUX86State *env, uint32_t new_cr4) > tlb_flush(env, 1); > } > /* SSE handling */ > - if (!(env->cpuid_features & CPUID_SSE)) { > + if (!(env->features[FEAT_1_EDX] & CPUID_SSE)) { > new_cr4 &= ~CR4_OSFXSR_MASK; > } > env->hflags &= ~HF_OSFXSR_MASK; > @@ -457,7 +457,7 @@ void cpu_x86_update_cr4(CPUX86State *env, uint32_t new_cr4) > env->hflags |= HF_OSFXSR_MASK; > } > > - if (!(env->cpuid_7_0_ebx_features & CPUID_7_0_EBX_SMAP)) { > + if (!(env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_SMAP)) { > new_cr4 &= ~CR4_SMAP_MASK; > } > env->hflags &= ~HF_SMAP_MASK; > diff --git a/target-i386/kvm.c b/target-i386/kvm.c > index 3acff40..11bd906 100644 > --- a/target-i386/kvm.c > +++ b/target-i386/kvm.c > @@ -445,7 +445,7 @@ int kvm_arch_init_vcpu(CPUState *cs) > c = &cpuid_data.entries[cpuid_i++]; > memset(c, 0, sizeof(*c)); > c->function = KVM_CPUID_FEATURES; > - c->eax = env->cpuid_kvm_features; > + c->eax = env->features[FEAT_KVM]; > > if (hyperv_enabled()) { > memcpy(signature, "Hv#1\0\0\0\0\0\0\0\0", 12); > @@ -580,7 +580,8 @@ int kvm_arch_init_vcpu(CPUState *cs) > cpuid_data.cpuid.nent = cpuid_i; > > if (((env->cpuid_version >> 8)&0xF) >= 6 > - && (env->cpuid_features&(CPUID_MCE|CPUID_MCA)) == (CPUID_MCE|CPUID_MCA) > + && (env->features[FEAT_1_EDX] & (CPUID_MCE|CPUID_MCA)) == > + (CPUID_MCE|CPUID_MCA) > && kvm_check_extension(cs->kvm_state, KVM_CAP_MCE) > 0) { > uint64_t mcg_cap; > int banks; > diff --git a/target-i386/misc_helper.c b/target-i386/misc_helper.c > index 719cacd..4fc4261 100644 > --- a/target-i386/misc_helper.c > +++ b/target-i386/misc_helper.c > @@ -291,22 +291,22 @@ void helper_wrmsr(CPUX86State *env) > uint64_t update_mask; > > update_mask = 0; > - if (env->cpuid_ext2_features & CPUID_EXT2_SYSCALL) { > + if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_SYSCALL) { > update_mask |= MSR_EFER_SCE; > } > - if (env->cpuid_ext2_features & CPUID_EXT2_LM) { > + if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_LM) { > update_mask |= MSR_EFER_LME; > } > - if (env->cpuid_ext2_features & CPUID_EXT2_FFXSR) { > + if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_FFXSR) { > update_mask |= MSR_EFER_FFXSR; > } > - if (env->cpuid_ext2_features & CPUID_EXT2_NX) { > + if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_NX) { > update_mask |= MSR_EFER_NXE; > } > - if (env->cpuid_ext3_features & CPUID_EXT3_SVM) { > + if (env->features[FEAT_8000_0001_ECX] & CPUID_EXT3_SVM) { > update_mask |= MSR_EFER_SVME; > } > - if (env->cpuid_ext2_features & CPUID_EXT2_FFXSR) { > + if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_FFXSR) { > update_mask |= MSR_EFER_FFXSR; > } > cpu_load_efer(env, (env->efer & ~update_mask) | > @@ -513,7 +513,7 @@ void helper_rdmsr(CPUX86State *env) > val = env->mtrr_deftype; > break; > case MSR_MTRRcap: > - if (env->cpuid_features & CPUID_MTRR) { > + if (env->features[FEAT_1_EDX] & CPUID_MTRR) { > val = MSR_MTRRcap_VCNT | MSR_MTRRcap_FIXRANGE_SUPPORT | > MSR_MTRRcap_WC_SUPPORTED; > } else { > diff --git a/target-i386/translate.c b/target-i386/translate.c > index 32d21f5..2d45ad4 100644 > --- a/target-i386/translate.c > +++ b/target-i386/translate.c > @@ -7926,11 +7926,11 @@ static inline void gen_intermediate_code_internal(CPUX86State *env, > if (flags & HF_SOFTMMU_MASK) { > dc->mem_index = (cpu_mmu_index(env) + 1) << 2; > } > - dc->cpuid_features = env->cpuid_features; > - dc->cpuid_ext_features = env->cpuid_ext_features; > - dc->cpuid_ext2_features = env->cpuid_ext2_features; > - dc->cpuid_ext3_features = env->cpuid_ext3_features; > - dc->cpuid_7_0_ebx_features = env->cpuid_7_0_ebx_features; > + dc->cpuid_features = env->features[FEAT_1_EDX]; > + dc->cpuid_ext_features = env->features[FEAT_1_ECX]; > + dc->cpuid_ext2_features = env->features[FEAT_8000_0001_EDX]; > + dc->cpuid_ext3_features = env->features[FEAT_8000_0001_ECX]; > + dc->cpuid_7_0_ebx_features = env->features[FEAT_7_0_EBX]; > #ifdef TARGET_X86_64 > dc->lma = (flags >> HF_LMA_SHIFT) & 1; > dc->code64 = (flags >> HF_CS64_SHIFT) & 1;
diff --git a/bsd-user/elfload.c b/bsd-user/elfload.c index a6cd3ab..44e1568 100644 --- a/bsd-user/elfload.c +++ b/bsd-user/elfload.c @@ -110,7 +110,7 @@ static const char *get_elf_platform(void) static uint32_t get_elf_hwcap(void) { - return thread_env->cpuid_features; + return thread_env->features[FEAT_1_EDX]; } #ifdef TARGET_X86_64 diff --git a/bsd-user/main.c b/bsd-user/main.c index 1dc0330..8b8b1f1 100644 --- a/bsd-user/main.c +++ b/bsd-user/main.c @@ -1010,13 +1010,13 @@ int main(int argc, char **argv) env->cr[0] = CR0_PG_MASK | CR0_WP_MASK | CR0_PE_MASK; env->hflags |= HF_PE_MASK; - if (env->cpuid_features & CPUID_SSE) { + if (env->features[FEAT_1_EDX] & CPUID_SSE) { env->cr[4] |= CR4_OSFXSR_MASK; env->hflags |= HF_OSFXSR_MASK; } #ifndef TARGET_ABI32 /* enable 64 bit mode if possible */ - if (!(env->cpuid_ext2_features & CPUID_EXT2_LM)) { + if (!(env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_LM)) { fprintf(stderr, "The selected x86 CPU does not support 64 bit mode\n"); exit(1); } diff --git a/hw/kvm/clock.c b/hw/kvm/clock.c index be24973..6d0777a 100644 --- a/hw/kvm/clock.c +++ b/hw/kvm/clock.c @@ -129,7 +129,7 @@ static TypeInfo kvmclock_info = { void kvmclock_create(void) { if (kvm_enabled() && - first_cpu->cpuid_kvm_features & ((1ULL << KVM_FEATURE_CLOCKSOURCE) | + first_cpu->features[FEAT_KVM] & ((1ULL << KVM_FEATURE_CLOCKSOURCE) | (1ULL << KVM_FEATURE_CLOCKSOURCE2))) { sysbus_create_simple("kvmclock", -1, NULL); } diff --git a/linux-user/elfload.c b/linux-user/elfload.c index 89db49c..04755de 100644 --- a/linux-user/elfload.c +++ b/linux-user/elfload.c @@ -130,7 +130,7 @@ static const char *get_elf_platform(void) static uint32_t get_elf_hwcap(void) { - return thread_env->cpuid_features; + return thread_env->features[FEAT_1_EDX]; } #ifdef TARGET_X86_64 diff --git a/linux-user/main.c b/linux-user/main.c index 9ade1bf..faed8c8 100644 --- a/linux-user/main.c +++ b/linux-user/main.c @@ -3630,13 +3630,13 @@ int main(int argc, char **argv, char **envp) env->cr[0] = CR0_PG_MASK | CR0_WP_MASK | CR0_PE_MASK; env->hflags |= HF_PE_MASK; - if (env->cpuid_features & CPUID_SSE) { + if (env->features[FEAT_1_EDX] & CPUID_SSE) { env->cr[4] |= CR4_OSFXSR_MASK; env->hflags |= HF_OSFXSR_MASK; } #ifndef TARGET_ABI32 /* enable 64 bit mode if possible */ - if (!(env->cpuid_ext2_features & CPUID_EXT2_LM)) { + if (!(env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_LM)) { fprintf(stderr, "The selected x86 CPU does not support 64 bit mode\n"); exit(1); } diff --git a/target-i386/cpu.c b/target-i386/cpu.c index 0b44dea..f4878bf 100644 --- a/target-i386/cpu.c +++ b/target-i386/cpu.c @@ -340,22 +340,15 @@ static void add_flagname_to_bitmaps(const char *flagname, typedef struct x86_def_t { struct x86_def_t *next; const char *name; - uint32_t level; + uint32_t level, xlevel, xlevel2; + FeatureWordArray features; uint32_t vendor1, vendor2, vendor3; int family; int model; int stepping; int tsc_khz; - uint32_t features, ext_features, ext2_features, ext3_features; - uint32_t kvm_features, svm_features; - uint32_t xlevel; char model_id[48]; int vendor_override; - /* Store the results of Centaur's CPUID instructions */ - uint32_t ext4_features; - uint32_t xlevel2; - /* The feature bits on CPUID[EAX=7,ECX=0].EBX */ - uint32_t cpuid_7_0_ebx_features; } x86_def_t; #define I486_FEATURES (CPUID_FP87 | CPUID_VME | CPUID_PSE) @@ -412,13 +405,14 @@ static x86_def_t builtin_x86_defs[] = { .family = 6, .model = 2, .stepping = 3, - .features = PPRO_FEATURES | - CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | - CPUID_PSE36, - .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_CX16 | CPUID_EXT_POPCNT, - .ext2_features = (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | - CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX, - .ext3_features = CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM | + .features[FEAT_1_EDX] = PPRO_FEATURES | CPUID_MTRR | CPUID_CLFLUSH | + CPUID_MCA | CPUID_PSE36, + .features[FEAT_1_ECX] = CPUID_EXT_SSE3 | CPUID_EXT_CX16 | + CPUID_EXT_POPCNT, + .features[FEAT_8000_0001_EDX] = + (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | CPUID_EXT2_LM | + CPUID_EXT2_SYSCALL | CPUID_EXT2_NX, + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM | CPUID_EXT3_ABM | CPUID_EXT3_SSE4A, .xlevel = 0x8000000A, }, @@ -431,22 +425,22 @@ static x86_def_t builtin_x86_defs[] = { .family = 16, .model = 2, .stepping = 3, - .features = PPRO_FEATURES | - CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | - CPUID_PSE36 | CPUID_VME | CPUID_HT, - .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_CX16 | - CPUID_EXT_POPCNT, - .ext2_features = (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | - CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX | - CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT | CPUID_EXT2_MMXEXT | - CPUID_EXT2_FFXSR | CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP, + .features[FEAT_1_EDX] = PPRO_FEATURES | CPUID_MTRR | CPUID_CLFLUSH | + CPUID_MCA | CPUID_PSE36 | CPUID_VME | CPUID_HT, + .features[FEAT_1_ECX] = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | + CPUID_EXT_CX16 | CPUID_EXT_POPCNT, + .features[FEAT_8000_0001_EDX] = + (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | CPUID_EXT2_LM | + CPUID_EXT2_SYSCALL | CPUID_EXT2_NX | CPUID_EXT2_3DNOW | + CPUID_EXT2_3DNOWEXT | CPUID_EXT2_MMXEXT | CPUID_EXT2_FFXSR | + CPUID_EXT2_PDPE1GB | CPUID_EXT2_RDTSCP, /* Missing: CPUID_EXT3_CMP_LEG, CPUID_EXT3_EXTAPIC, CPUID_EXT3_CR8LEG, CPUID_EXT3_MISALIGNSSE, CPUID_EXT3_3DNOWPREFETCH, CPUID_EXT3_OSVW, CPUID_EXT3_IBS */ - .ext3_features = CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM | + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM | CPUID_EXT3_SVM | CPUID_EXT3_ABM | CPUID_EXT3_SSE4A, - .svm_features = CPUID_SVM_NPT | CPUID_SVM_LBRV, + .features[FEAT_SVM] = CPUID_SVM_NPT | CPUID_SVM_LBRV, .xlevel = 0x8000001A, .model_id = "AMD Phenom(tm) 9550 Quad-Core Processor" }, @@ -459,15 +453,16 @@ static x86_def_t builtin_x86_defs[] = { .family = 6, .model = 15, .stepping = 11, - .features = PPRO_FEATURES | - CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | - CPUID_PSE36 | CPUID_VME | CPUID_DTS | CPUID_ACPI | CPUID_SS | - CPUID_HT | CPUID_TM | CPUID_PBE, - .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_SSSE3 | - CPUID_EXT_DTES64 | CPUID_EXT_DSCPL | CPUID_EXT_VMX | CPUID_EXT_EST | - CPUID_EXT_TM2 | CPUID_EXT_CX16 | CPUID_EXT_XTPR | CPUID_EXT_PDCM, - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX, - .ext3_features = CPUID_EXT3_LAHF_LM, + .features[FEAT_1_EDX] = PPRO_FEATURES | CPUID_MTRR | CPUID_CLFLUSH | + CPUID_MCA | CPUID_PSE36 | CPUID_VME | CPUID_DTS | CPUID_ACPI | + CPUID_SS | CPUID_HT | CPUID_TM | CPUID_PBE, + .features[FEAT_1_ECX] = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | + CPUID_EXT_SSSE3 | CPUID_EXT_DTES64 | CPUID_EXT_DSCPL | + CPUID_EXT_VMX | CPUID_EXT_EST | CPUID_EXT_TM2 | CPUID_EXT_CX16 | + CPUID_EXT_XTPR | CPUID_EXT_PDCM, + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | + CPUID_EXT2_NX, + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM, .xlevel = 0x80000008, .model_id = "Intel(R) Core(TM)2 Duo CPU T7700 @ 2.40GHz", }, @@ -481,19 +476,19 @@ static x86_def_t builtin_x86_defs[] = { .model = 6, .stepping = 1, /* Missing: CPUID_VME, CPUID_HT */ - .features = PPRO_FEATURES | - CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | - CPUID_PSE36, + .features[FEAT_1_EDX] = PPRO_FEATURES | CPUID_MTRR | CPUID_CLFLUSH | + CPUID_MCA | CPUID_PSE36, /* Missing: CPUID_EXT_POPCNT, CPUID_EXT_MONITOR */ - .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_CX16, + .features[FEAT_1_ECX] = CPUID_EXT_SSE3 | CPUID_EXT_CX16, /* Missing: CPUID_EXT2_PDPE1GB, CPUID_EXT2_RDTSCP */ - .ext2_features = (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | - CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX, + .features[FEAT_8000_0001_EDX] = + (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | CPUID_EXT2_LM | + CPUID_EXT2_SYSCALL | CPUID_EXT2_NX, /* Missing: CPUID_EXT3_LAHF_LM, CPUID_EXT3_CMP_LEG, CPUID_EXT3_EXTAPIC, CPUID_EXT3_CR8LEG, CPUID_EXT3_ABM, CPUID_EXT3_SSE4A, CPUID_EXT3_MISALIGNSSE, CPUID_EXT3_3DNOWPREFETCH, CPUID_EXT3_OSVW, CPUID_EXT3_IBS, CPUID_EXT3_SVM */ - .ext3_features = 0, + .features[FEAT_8000_0001_ECX] = 0, .xlevel = 0x80000008, .model_id = "Common KVM processor" }, @@ -506,8 +501,8 @@ static x86_def_t builtin_x86_defs[] = { .family = 6, .model = 3, .stepping = 3, - .features = PPRO_FEATURES, - .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_POPCNT, + .features[FEAT_1_EDX] = PPRO_FEATURES, + .features[FEAT_1_ECX] = CPUID_EXT_SSE3 | CPUID_EXT_POPCNT, .xlevel = 0x80000004, }, { @@ -519,11 +514,11 @@ static x86_def_t builtin_x86_defs[] = { .family = 15, .model = 6, .stepping = 1, - .features = PPRO_FEATURES | - CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_PSE36, - .ext_features = CPUID_EXT_SSE3, - .ext2_features = PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES, - .ext3_features = 0, + .features[FEAT_1_EDX] = PPRO_FEATURES | CPUID_MTRR | CPUID_CLFLUSH | + CPUID_MCA | CPUID_PSE36, + .features[FEAT_1_ECX] = CPUID_EXT_SSE3, + .features[FEAT_8000_0001_EDX] = PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES, + .features[FEAT_8000_0001_ECX] = 0, .xlevel = 0x80000008, .model_id = "Common 32-bit KVM processor" }, @@ -536,12 +531,13 @@ static x86_def_t builtin_x86_defs[] = { .family = 6, .model = 14, .stepping = 8, - .features = PPRO_FEATURES | CPUID_VME | - CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_DTS | CPUID_ACPI | - CPUID_SS | CPUID_HT | CPUID_TM | CPUID_PBE, - .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_VMX | - CPUID_EXT_EST | CPUID_EXT_TM2 | CPUID_EXT_XTPR | CPUID_EXT_PDCM, - .ext2_features = CPUID_EXT2_NX, + .features[FEAT_1_EDX] = PPRO_FEATURES | CPUID_VME | CPUID_MTRR | + CPUID_CLFLUSH | CPUID_MCA | CPUID_DTS | CPUID_ACPI | CPUID_SS | + CPUID_HT | CPUID_TM | CPUID_PBE, + .features[FEAT_1_ECX] = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | + CPUID_EXT_VMX | CPUID_EXT_EST | CPUID_EXT_TM2 | CPUID_EXT_XTPR | + CPUID_EXT_PDCM, + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_NX, .xlevel = 0x80000008, .model_id = "Genuine Intel(R) CPU T2600 @ 2.16GHz", }, @@ -554,7 +550,7 @@ static x86_def_t builtin_x86_defs[] = { .family = 4, .model = 0, .stepping = 0, - .features = I486_FEATURES, + .features[FEAT_1_EDX] = I486_FEATURES, .xlevel = 0, }, { @@ -566,7 +562,7 @@ static x86_def_t builtin_x86_defs[] = { .family = 5, .model = 4, .stepping = 3, - .features = PENTIUM_FEATURES, + .features[FEAT_1_EDX] = PENTIUM_FEATURES, .xlevel = 0, }, { @@ -578,7 +574,7 @@ static x86_def_t builtin_x86_defs[] = { .family = 6, .model = 5, .stepping = 2, - .features = PENTIUM2_FEATURES, + .features[FEAT_1_EDX] = PENTIUM2_FEATURES, .xlevel = 0, }, { @@ -590,7 +586,7 @@ static x86_def_t builtin_x86_defs[] = { .family = 6, .model = 7, .stepping = 3, - .features = PENTIUM3_FEATURES, + .features[FEAT_1_EDX] = PENTIUM3_FEATURES, .xlevel = 0, }, { @@ -602,10 +598,11 @@ static x86_def_t builtin_x86_defs[] = { .family = 6, .model = 2, .stepping = 3, - .features = PPRO_FEATURES | CPUID_PSE36 | CPUID_VME | CPUID_MTRR | - CPUID_MCA, - .ext2_features = (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | - CPUID_EXT2_MMXEXT | CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT, + .features[FEAT_1_EDX] = PPRO_FEATURES | CPUID_PSE36 | CPUID_VME | + CPUID_MTRR | CPUID_MCA, + .features[FEAT_8000_0001_EDX] = + (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | CPUID_EXT2_MMXEXT | + CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT, .xlevel = 0x80000008, }, { @@ -618,15 +615,16 @@ static x86_def_t builtin_x86_defs[] = { .family = 6, .model = 28, .stepping = 2, - .features = PPRO_FEATURES | - CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_VME | CPUID_DTS | - CPUID_ACPI | CPUID_SS | CPUID_HT | CPUID_TM | CPUID_PBE, + .features[FEAT_1_EDX] = PPRO_FEATURES | CPUID_MTRR | CPUID_CLFLUSH | + CPUID_MCA | CPUID_VME | CPUID_DTS | CPUID_ACPI | CPUID_SS | + CPUID_HT | CPUID_TM | CPUID_PBE, /* Some CPUs got no CPUID_SEP */ - .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_SSSE3 | - CPUID_EXT_DSCPL | CPUID_EXT_EST | CPUID_EXT_TM2 | CPUID_EXT_XTPR, - .ext2_features = (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | - CPUID_EXT2_NX, - .ext3_features = CPUID_EXT3_LAHF_LM, + .features[FEAT_1_ECX] = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | + CPUID_EXT_SSSE3 | CPUID_EXT_DSCPL | CPUID_EXT_EST | CPUID_EXT_TM2 | + CPUID_EXT_XTPR, + .features[FEAT_8000_0001_EDX] = + (PPRO_FEATURES & CPUID_EXT2_AMD_ALIASES) | CPUID_EXT2_NX, + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM, .xlevel = 0x8000000A, .model_id = "Intel(R) Atom(TM) CPU N270 @ 1.60GHz", }, @@ -639,14 +637,15 @@ static x86_def_t builtin_x86_defs[] = { .family = 6, .model = 2, .stepping = 3, - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | - CPUID_DE | CPUID_FP87, - .ext_features = CPUID_EXT_SSSE3 | CPUID_EXT_SSE3, - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL, - .ext3_features = CPUID_EXT3_LAHF_LM, + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | + CPUID_PSE | CPUID_DE | CPUID_FP87, + .features[FEAT_1_ECX] = CPUID_EXT_SSSE3 | CPUID_EXT_SSE3, + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_NX | + CPUID_EXT2_SYSCALL, + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM, .xlevel = 0x8000000A, .model_id = "Intel Celeron_4x0 (Conroe/Merom Class Core 2)", }, @@ -659,15 +658,16 @@ static x86_def_t builtin_x86_defs[] = { .family = 6, .model = 2, .stepping = 3, - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | - CPUID_DE | CPUID_FP87, - .ext_features = CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | - CPUID_EXT_SSE3, - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_NX | CPUID_EXT2_SYSCALL, - .ext3_features = CPUID_EXT3_LAHF_LM, + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | + CPUID_PSE | CPUID_DE | CPUID_FP87, + .features[FEAT_1_ECX] = CPUID_EXT_SSE41 | CPUID_EXT_CX16 | + CPUID_EXT_SSSE3 | CPUID_EXT_SSE3, + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_NX | + CPUID_EXT2_SYSCALL, + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM, .xlevel = 0x8000000A, .model_id = "Intel Core 2 Duo P9xxx (Penryn Class Core 2)", }, @@ -680,15 +680,17 @@ static x86_def_t builtin_x86_defs[] = { .family = 6, .model = 2, .stepping = 3, - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | - CPUID_DE | CPUID_FP87, - .ext_features = CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 | - CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_SSE3, - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX, - .ext3_features = CPUID_EXT3_LAHF_LM, + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | + CPUID_PSE | CPUID_DE | CPUID_FP87, + .features[FEAT_1_ECX] = CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | + CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | + CPUID_EXT_SSE3, + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | + CPUID_EXT2_NX, + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM, .xlevel = 0x8000000A, .model_id = "Intel Core i7 9xx (Nehalem Class Core i7)", }, @@ -701,16 +703,17 @@ static x86_def_t builtin_x86_defs[] = { .family = 6, .model = 44, .stepping = 1, - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | - CPUID_DE | CPUID_FP87, - .ext_features = CPUID_EXT_AES | CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | - CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | - CPUID_EXT_SSE3, - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX, - .ext3_features = CPUID_EXT3_LAHF_LM, + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | + CPUID_PSE | CPUID_DE | CPUID_FP87, + .features[FEAT_1_ECX] = CPUID_EXT_AES | CPUID_EXT_POPCNT | + CPUID_EXT_SSE42 | CPUID_EXT_SSE41 | CPUID_EXT_CX16 | + CPUID_EXT_SSSE3 | CPUID_EXT_SSE3, + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | + CPUID_EXT2_NX, + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM, .xlevel = 0x8000000A, .model_id = "Westmere E56xx/L56xx/X56xx (Nehalem-C)", }, @@ -723,19 +726,19 @@ static x86_def_t builtin_x86_defs[] = { .family = 6, .model = 42, .stepping = 1, - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | - CPUID_DE | CPUID_FP87, - .ext_features = CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES | - CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_POPCNT | - CPUID_EXT_X2APIC | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 | - CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ | - CPUID_EXT_SSE3, - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX | - CPUID_EXT2_SYSCALL, - .ext3_features = CPUID_EXT3_LAHF_LM, + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | + CPUID_PSE | CPUID_DE | CPUID_FP87, + .features[FEAT_1_ECX] = CPUID_EXT_AVX | CPUID_EXT_XSAVE | + CPUID_EXT_AES | CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_POPCNT | + CPUID_EXT_X2APIC | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 | + CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ | + CPUID_EXT_SSE3, + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | + CPUID_EXT2_NX | CPUID_EXT2_SYSCALL, + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM, .xlevel = 0x8000000A, .model_id = "Intel Xeon E312xx (Sandy Bridge)", }, @@ -748,21 +751,21 @@ static x86_def_t builtin_x86_defs[] = { .family = 6, .model = 60, .stepping = 1, - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | - CPUID_DE | CPUID_FP87, - .ext_features = CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES | - CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | CPUID_EXT_SSE42 | - CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | - CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 | - CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE | - CPUID_EXT_PCID, - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_NX | - CPUID_EXT2_SYSCALL, - .ext3_features = CPUID_EXT3_LAHF_LM, - .cpuid_7_0_ebx_features = CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | + CPUID_PSE | CPUID_DE | CPUID_FP87, + .features[FEAT_1_ECX] = CPUID_EXT_AVX | CPUID_EXT_XSAVE | + CPUID_EXT_AES | CPUID_EXT_POPCNT | CPUID_EXT_X2APIC | + CPUID_EXT_SSE42 | CPUID_EXT_SSE41 | CPUID_EXT_CX16 | + CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3 | + CPUID_EXT_TSC_DEADLINE_TIMER | CPUID_EXT_FMA | CPUID_EXT_MOVBE | + CPUID_EXT_PCID, + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | + CPUID_EXT2_NX | CPUID_EXT2_SYSCALL, + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_LAHF_LM, + .features[FEAT_7_0_EBX] = CPUID_7_0_EBX_FSGSBASE | CPUID_7_0_EBX_BMI1 | CPUID_7_0_EBX_HLE | CPUID_7_0_EBX_AVX2 | CPUID_7_0_EBX_SMEP | CPUID_7_0_EBX_BMI2 | CPUID_7_0_EBX_ERMS | CPUID_7_0_EBX_INVPCID | CPUID_7_0_EBX_RTM, @@ -778,18 +781,18 @@ static x86_def_t builtin_x86_defs[] = { .family = 15, .model = 6, .stepping = 1, - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | - CPUID_DE | CPUID_FP87, - .ext_features = CPUID_EXT_SSE3, - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_FXSR | CPUID_EXT2_MMX | - CPUID_EXT2_NX | CPUID_EXT2_PSE36 | CPUID_EXT2_PAT | + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | + CPUID_PSE | CPUID_DE | CPUID_FP87, + .features[FEAT_1_ECX] = CPUID_EXT_SSE3, + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_FXSR | + CPUID_EXT2_MMX | CPUID_EXT2_NX | CPUID_EXT2_PSE36 | CPUID_EXT2_PAT | CPUID_EXT2_CMOV | CPUID_EXT2_MCA | CPUID_EXT2_PGE | - CPUID_EXT2_MTRR | CPUID_EXT2_SYSCALL | CPUID_EXT2_APIC | - CPUID_EXT2_CX8 | CPUID_EXT2_MCE | CPUID_EXT2_PAE | CPUID_EXT2_MSR | - CPUID_EXT2_TSC | CPUID_EXT2_PSE | CPUID_EXT2_DE | CPUID_EXT2_FPU, + CPUID_EXT2_MTRR | CPUID_EXT2_SYSCALL | CPUID_EXT2_APIC | + CPUID_EXT2_CX8 | CPUID_EXT2_MCE | CPUID_EXT2_PAE | CPUID_EXT2_MSR | + CPUID_EXT2_TSC | CPUID_EXT2_PSE | CPUID_EXT2_DE | CPUID_EXT2_FPU, .xlevel = 0x80000008, .model_id = "AMD Opteron 240 (Gen 1 Class Opteron)", }, @@ -802,20 +805,20 @@ static x86_def_t builtin_x86_defs[] = { .family = 15, .model = 6, .stepping = 1, - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | - CPUID_DE | CPUID_FP87, - .ext_features = CPUID_EXT_CX16 | CPUID_EXT_SSE3, - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_FXSR | - CPUID_EXT2_MMX | CPUID_EXT2_NX | CPUID_EXT2_PSE36 | - CPUID_EXT2_PAT | CPUID_EXT2_CMOV | CPUID_EXT2_MCA | - CPUID_EXT2_PGE | CPUID_EXT2_MTRR | CPUID_EXT2_SYSCALL | - CPUID_EXT2_APIC | CPUID_EXT2_CX8 | CPUID_EXT2_MCE | - CPUID_EXT2_PAE | CPUID_EXT2_MSR | CPUID_EXT2_TSC | CPUID_EXT2_PSE | - CPUID_EXT2_DE | CPUID_EXT2_FPU, - .ext3_features = CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM, + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | + CPUID_PSE | CPUID_DE | CPUID_FP87, + .features[FEAT_1_ECX] = CPUID_EXT_CX16 | CPUID_EXT_SSE3, + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | + CPUID_EXT2_FXSR | CPUID_EXT2_MMX | CPUID_EXT2_NX | + CPUID_EXT2_PSE36 | CPUID_EXT2_PAT | CPUID_EXT2_CMOV | + CPUID_EXT2_MCA | CPUID_EXT2_PGE | CPUID_EXT2_MTRR | + CPUID_EXT2_SYSCALL | CPUID_EXT2_APIC | CPUID_EXT2_CX8 | + CPUID_EXT2_MCE | CPUID_EXT2_PAE | CPUID_EXT2_MSR | CPUID_EXT2_TSC | + CPUID_EXT2_PSE | CPUID_EXT2_DE | CPUID_EXT2_FPU, + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM, .xlevel = 0x80000008, .model_id = "AMD Opteron 22xx (Gen 2 Class Opteron)", }, @@ -828,22 +831,23 @@ static x86_def_t builtin_x86_defs[] = { .family = 15, .model = 6, .stepping = 1, - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | - CPUID_DE | CPUID_FP87, - .ext_features = CPUID_EXT_POPCNT | CPUID_EXT_CX16 | CPUID_EXT_MONITOR | - CPUID_EXT_SSE3, - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | CPUID_EXT2_FXSR | - CPUID_EXT2_MMX | CPUID_EXT2_NX | CPUID_EXT2_PSE36 | - CPUID_EXT2_PAT | CPUID_EXT2_CMOV | CPUID_EXT2_MCA | - CPUID_EXT2_PGE | CPUID_EXT2_MTRR | CPUID_EXT2_SYSCALL | - CPUID_EXT2_APIC | CPUID_EXT2_CX8 | CPUID_EXT2_MCE | - CPUID_EXT2_PAE | CPUID_EXT2_MSR | CPUID_EXT2_TSC | CPUID_EXT2_PSE | - CPUID_EXT2_DE | CPUID_EXT2_FPU, - .ext3_features = CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | - CPUID_EXT3_ABM | CPUID_EXT3_SVM | CPUID_EXT3_LAHF_LM, + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | + CPUID_PSE | CPUID_DE | CPUID_FP87, + .features[FEAT_1_ECX] = CPUID_EXT_POPCNT | CPUID_EXT_CX16 | + CPUID_EXT_MONITOR | CPUID_EXT_SSE3, + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | + CPUID_EXT2_FXSR | CPUID_EXT2_MMX | CPUID_EXT2_NX | + CPUID_EXT2_PSE36 | CPUID_EXT2_PAT | CPUID_EXT2_CMOV | + CPUID_EXT2_MCA | CPUID_EXT2_PGE | CPUID_EXT2_MTRR | + CPUID_EXT2_SYSCALL | CPUID_EXT2_APIC | CPUID_EXT2_CX8 | + CPUID_EXT2_MCE | CPUID_EXT2_PAE | CPUID_EXT2_MSR | CPUID_EXT2_TSC | + CPUID_EXT2_PSE | CPUID_EXT2_DE | CPUID_EXT2_FPU, + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_MISALIGNSSE | + CPUID_EXT3_SSE4A | CPUID_EXT3_ABM | CPUID_EXT3_SVM | + CPUID_EXT3_LAHF_LM, .xlevel = 0x80000008, .model_id = "AMD Opteron 23xx (Gen 3 Class Opteron)", }, @@ -856,26 +860,26 @@ static x86_def_t builtin_x86_defs[] = { .family = 21, .model = 1, .stepping = 2, - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | - CPUID_DE | CPUID_FP87, - .ext_features = CPUID_EXT_AVX | CPUID_EXT_XSAVE | CPUID_EXT_AES | - CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | CPUID_EXT_SSE41 | - CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ | - CPUID_EXT_SSE3, - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | - CPUID_EXT2_PDPE1GB | CPUID_EXT2_FXSR | CPUID_EXT2_MMX | - CPUID_EXT2_NX | CPUID_EXT2_PSE36 | CPUID_EXT2_PAT | - CPUID_EXT2_CMOV | CPUID_EXT2_MCA | CPUID_EXT2_PGE | - CPUID_EXT2_MTRR | CPUID_EXT2_SYSCALL | CPUID_EXT2_APIC | - CPUID_EXT2_CX8 | CPUID_EXT2_MCE | CPUID_EXT2_PAE | CPUID_EXT2_MSR | - CPUID_EXT2_TSC | CPUID_EXT2_PSE | CPUID_EXT2_DE | CPUID_EXT2_FPU, - .ext3_features = CPUID_EXT3_FMA4 | CPUID_EXT3_XOP | - CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_MISALIGNSSE | - CPUID_EXT3_SSE4A | CPUID_EXT3_ABM | CPUID_EXT3_SVM | - CPUID_EXT3_LAHF_LM, + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | + CPUID_PSE | CPUID_DE | CPUID_FP87, + .features[FEAT_1_ECX] = CPUID_EXT_AVX | CPUID_EXT_XSAVE | + CPUID_EXT_AES | CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | + CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_SSSE3 | + CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3, + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | + CPUID_EXT2_PDPE1GB | CPUID_EXT2_FXSR | CPUID_EXT2_MMX | + CPUID_EXT2_NX | CPUID_EXT2_PSE36 | CPUID_EXT2_PAT | + CPUID_EXT2_CMOV | CPUID_EXT2_MCA | CPUID_EXT2_PGE | + CPUID_EXT2_MTRR | CPUID_EXT2_SYSCALL | CPUID_EXT2_APIC | + CPUID_EXT2_CX8 | CPUID_EXT2_MCE | CPUID_EXT2_PAE | CPUID_EXT2_MSR | + CPUID_EXT2_TSC | CPUID_EXT2_PSE | CPUID_EXT2_DE | CPUID_EXT2_FPU, + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_FMA4 | CPUID_EXT3_XOP | + CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_MISALIGNSSE | + CPUID_EXT3_SSE4A | CPUID_EXT3_ABM | CPUID_EXT3_SVM | + CPUID_EXT3_LAHF_LM, .xlevel = 0x8000001A, .model_id = "AMD Opteron 62xx class CPU", }, @@ -888,26 +892,26 @@ static x86_def_t builtin_x86_defs[] = { .family = 21, .model = 2, .stepping = 0, - .features = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX | - CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | CPUID_MCA | - CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | CPUID_CX8 | - CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | CPUID_PSE | - CPUID_DE | CPUID_FP87, - .ext_features = CPUID_EXT_F16C | CPUID_EXT_AVX | CPUID_EXT_XSAVE | - CPUID_EXT_AES | CPUID_EXT_POPCNT | CPUID_EXT_SSE42 | - CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_FMA | + .features[FEAT_1_EDX] = CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | + CPUID_MMX | CPUID_CLFLUSH | CPUID_PSE36 | CPUID_PAT | CPUID_CMOV | + CPUID_MCA | CPUID_PGE | CPUID_MTRR | CPUID_SEP | CPUID_APIC | + CPUID_CX8 | CPUID_MCE | CPUID_PAE | CPUID_MSR | CPUID_TSC | + CPUID_PSE | CPUID_DE | CPUID_FP87, + .features[FEAT_1_ECX] = CPUID_EXT_F16C | CPUID_EXT_AVX | + CPUID_EXT_XSAVE | CPUID_EXT_AES | CPUID_EXT_POPCNT | + CPUID_EXT_SSE42 | CPUID_EXT_SSE41 | CPUID_EXT_CX16 | CPUID_EXT_FMA | CPUID_EXT_SSSE3 | CPUID_EXT_PCLMULQDQ | CPUID_EXT_SSE3, - .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | - CPUID_EXT2_PDPE1GB | CPUID_EXT2_FXSR | CPUID_EXT2_MMX | - CPUID_EXT2_NX | CPUID_EXT2_PSE36 | CPUID_EXT2_PAT | - CPUID_EXT2_CMOV | CPUID_EXT2_MCA | CPUID_EXT2_PGE | - CPUID_EXT2_MTRR | CPUID_EXT2_SYSCALL | CPUID_EXT2_APIC | - CPUID_EXT2_CX8 | CPUID_EXT2_MCE | CPUID_EXT2_PAE | CPUID_EXT2_MSR | - CPUID_EXT2_TSC | CPUID_EXT2_PSE | CPUID_EXT2_DE | CPUID_EXT2_FPU, - .ext3_features = CPUID_EXT3_TBM | CPUID_EXT3_FMA4 | CPUID_EXT3_XOP | - CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_MISALIGNSSE | + .features[FEAT_8000_0001_EDX] = CPUID_EXT2_LM | CPUID_EXT2_RDTSCP | + CPUID_EXT2_PDPE1GB | CPUID_EXT2_FXSR | CPUID_EXT2_MMX | + CPUID_EXT2_NX | CPUID_EXT2_PSE36 | CPUID_EXT2_PAT | + CPUID_EXT2_CMOV | CPUID_EXT2_MCA | CPUID_EXT2_PGE | + CPUID_EXT2_MTRR | CPUID_EXT2_SYSCALL | CPUID_EXT2_APIC | + CPUID_EXT2_CX8 | CPUID_EXT2_MCE | CPUID_EXT2_PAE | CPUID_EXT2_MSR | + CPUID_EXT2_TSC | CPUID_EXT2_PSE | CPUID_EXT2_DE | CPUID_EXT2_FPU, + .features[FEAT_8000_0001_ECX] = CPUID_EXT3_TBM | CPUID_EXT3_FMA4 | + CPUID_EXT3_XOP | CPUID_EXT3_3DNOWPREFETCH | CPUID_EXT3_MISALIGNSSE | CPUID_EXT3_SSE4A | CPUID_EXT3_ABM | CPUID_EXT3_SVM | - CPUID_EXT3_LAHF_LM, + CPUID_EXT3_LAHF_LM, .xlevel = 0x8000001A, .model_id = "AMD Opteron 63xx class CPU", }, @@ -955,20 +959,22 @@ static void kvm_cpu_fill_host(x86_def_t *x86_cpu_def) x86_cpu_def->stepping = eax & 0x0F; x86_cpu_def->level = kvm_arch_get_supported_cpuid(s, 0x0, 0, R_EAX); - x86_cpu_def->features = kvm_arch_get_supported_cpuid(s, 0x1, 0, R_EDX); - x86_cpu_def->ext_features = kvm_arch_get_supported_cpuid(s, 0x1, 0, R_ECX); + x86_cpu_def->features[FEAT_1_EDX] = + kvm_arch_get_supported_cpuid(s, 0x1, 0, R_EDX); + x86_cpu_def->features[FEAT_1_ECX] = + kvm_arch_get_supported_cpuid(s, 0x1, 0, R_ECX); if (x86_cpu_def->level >= 7) { - x86_cpu_def->cpuid_7_0_ebx_features = + x86_cpu_def->features[FEAT_7_0_EBX] = kvm_arch_get_supported_cpuid(s, 0x7, 0, R_EBX); } else { - x86_cpu_def->cpuid_7_0_ebx_features = 0; + x86_cpu_def->features[FEAT_7_0_EBX] = 0; } x86_cpu_def->xlevel = kvm_arch_get_supported_cpuid(s, 0x80000000, 0, R_EAX); - x86_cpu_def->ext2_features = + x86_cpu_def->features[FEAT_8000_0001_EDX] = kvm_arch_get_supported_cpuid(s, 0x80000001, 0, R_EDX); - x86_cpu_def->ext3_features = + x86_cpu_def->features[FEAT_8000_0001_ECX] = kvm_arch_get_supported_cpuid(s, 0x80000001, 0, R_ECX); cpu_x86_fill_model_id(x86_cpu_def->model_id); @@ -984,15 +990,15 @@ static void kvm_cpu_fill_host(x86_def_t *x86_cpu_def) /* Support VIA max extended level */ x86_cpu_def->xlevel2 = eax; host_cpuid(0xC0000001, 0, &eax, &ebx, &ecx, &edx); - x86_cpu_def->ext4_features = + x86_cpu_def->features[FEAT_C000_0001_EDX] = kvm_arch_get_supported_cpuid(s, 0xC0000001, 0, R_EDX); } } /* Other KVM-specific feature fields: */ - x86_cpu_def->svm_features = + x86_cpu_def->features[FEAT_SVM] = kvm_arch_get_supported_cpuid(s, 0x8000000A, 0, R_EDX); - x86_cpu_def->kvm_features = + x86_cpu_def->features[FEAT_KVM] = kvm_arch_get_supported_cpuid(s, KVM_CPUID_FEATURES, 0, R_EAX); #endif /* CONFIG_KVM */ @@ -1028,21 +1034,29 @@ static int kvm_check_features_against_host(x86_def_t *guest_def) uint32_t mask; int rv, i; struct model_features_t ft[] = { - {&guest_def->features, &host_def.features, + {&guest_def->features[FEAT_1_EDX], + &host_def.features[FEAT_1_EDX], FEAT_1_EDX }, - {&guest_def->ext_features, &host_def.ext_features, + {&guest_def->features[FEAT_1_ECX], + &host_def.features[FEAT_1_ECX], FEAT_1_ECX }, - {&guest_def->ext2_features, &host_def.ext2_features, + {&guest_def->features[FEAT_8000_0001_EDX], + &host_def.features[FEAT_8000_0001_EDX], FEAT_8000_0001_EDX }, - {&guest_def->ext3_features, &host_def.ext3_features, + {&guest_def->features[FEAT_8000_0001_ECX], + &host_def.features[FEAT_8000_0001_ECX], FEAT_8000_0001_ECX }, - {&guest_def->ext4_features, &host_def.ext4_features, + {&guest_def->features[FEAT_C000_0001_EDX], + &host_def.features[FEAT_C000_0001_EDX], FEAT_C000_0001_EDX }, - {&guest_def->cpuid_7_0_ebx_features, &host_def.cpuid_7_0_ebx_features, + {&guest_def->features[FEAT_7_0_EBX], + &host_def.features[FEAT_7_0_EBX], FEAT_7_0_EBX }, - {&guest_def->svm_features, &host_def.svm_features, + {&guest_def->features[FEAT_SVM], + &host_def.features[FEAT_SVM], FEAT_SVM }, - {&guest_def->kvm_features, &host_def.kvm_features, + {&guest_def->features[FEAT_KVM], + &host_def.features[FEAT_KVM], FEAT_KVM }, }; @@ -1459,22 +1473,28 @@ static int cpu_x86_parse_featurestr(x86_def_t *x86_cpu_def, char *features) } featurestr = strtok(NULL, ","); } - x86_cpu_def->features |= plus_features[FEAT_1_EDX]; - x86_cpu_def->ext_features |= plus_features[FEAT_1_ECX]; - x86_cpu_def->ext2_features |= plus_features[FEAT_8000_0001_EDX]; - x86_cpu_def->ext3_features |= plus_features[FEAT_8000_0001_ECX]; - x86_cpu_def->ext4_features |= plus_features[FEAT_C000_0001_EDX]; - x86_cpu_def->kvm_features |= plus_features[FEAT_KVM]; - x86_cpu_def->svm_features |= plus_features[FEAT_SVM]; - x86_cpu_def->cpuid_7_0_ebx_features |= plus_features[FEAT_7_0_EBX]; - x86_cpu_def->features &= ~minus_features[FEAT_1_EDX]; - x86_cpu_def->ext_features &= ~minus_features[FEAT_1_ECX]; - x86_cpu_def->ext2_features &= ~minus_features[FEAT_8000_0001_EDX]; - x86_cpu_def->ext3_features &= ~minus_features[FEAT_8000_0001_ECX]; - x86_cpu_def->ext4_features &= ~minus_features[FEAT_C000_0001_EDX]; - x86_cpu_def->kvm_features &= ~minus_features[FEAT_KVM]; - x86_cpu_def->svm_features &= ~minus_features[FEAT_SVM]; - x86_cpu_def->cpuid_7_0_ebx_features &= ~minus_features[FEAT_7_0_EBX]; + x86_cpu_def->features[FEAT_1_EDX] |= plus_features[FEAT_1_EDX]; + x86_cpu_def->features[FEAT_1_ECX] |= plus_features[FEAT_1_ECX]; + x86_cpu_def->features[FEAT_8000_0001_EDX] |= + plus_features[FEAT_8000_0001_EDX]; + x86_cpu_def->features[FEAT_8000_0001_ECX] |= + plus_features[FEAT_8000_0001_ECX]; + x86_cpu_def->features[FEAT_C000_0001_EDX] |= + plus_features[FEAT_C000_0001_EDX]; + x86_cpu_def->features[FEAT_KVM] |= plus_features[FEAT_KVM]; + x86_cpu_def->features[FEAT_SVM] |= plus_features[FEAT_SVM]; + x86_cpu_def->features[FEAT_7_0_EBX] |= plus_features[FEAT_7_0_EBX]; + x86_cpu_def->features[FEAT_1_EDX] &= ~minus_features[FEAT_1_EDX]; + x86_cpu_def->features[FEAT_1_ECX] &= ~minus_features[FEAT_1_ECX]; + x86_cpu_def->features[FEAT_8000_0001_EDX] &= + ~minus_features[FEAT_8000_0001_EDX]; + x86_cpu_def->features[FEAT_8000_0001_ECX] &= + ~minus_features[FEAT_8000_0001_ECX]; + x86_cpu_def->features[FEAT_C000_0001_EDX] &= + ~minus_features[FEAT_C000_0001_EDX]; + x86_cpu_def->features[FEAT_KVM] &= ~minus_features[FEAT_KVM]; + x86_cpu_def->features[FEAT_SVM] &= ~minus_features[FEAT_SVM]; + x86_cpu_def->features[FEAT_7_0_EBX] &= ~minus_features[FEAT_7_0_EBX]; if (check_cpuid && kvm_enabled()) { if (kvm_check_features_against_host(x86_cpu_def) && enforce_cpuid) goto error; @@ -1566,21 +1586,21 @@ static void filter_features_for_kvm(X86CPU *cpu) CPUX86State *env = &cpu->env; KVMState *s = kvm_state; - env->cpuid_features &= + env->features[FEAT_1_EDX] &= kvm_arch_get_supported_cpuid(s, 1, 0, R_EDX); - env->cpuid_ext_features &= + env->features[FEAT_1_ECX] &= kvm_arch_get_supported_cpuid(s, 1, 0, R_ECX); - env->cpuid_ext2_features &= + env->features[FEAT_8000_0001_EDX] &= kvm_arch_get_supported_cpuid(s, 0x80000001, 0, R_EDX); - env->cpuid_ext3_features &= + env->features[FEAT_8000_0001_ECX] &= kvm_arch_get_supported_cpuid(s, 0x80000001, 0, R_ECX); - env->cpuid_svm_features &= + env->features[FEAT_SVM] &= kvm_arch_get_supported_cpuid(s, 0x8000000A, 0, R_EDX); - env->cpuid_7_0_ebx_features &= + env->features[FEAT_7_0_EBX] &= kvm_arch_get_supported_cpuid(s, 7, 0, R_EBX); - env->cpuid_kvm_features &= + env->features[FEAT_KVM] &= kvm_arch_get_supported_cpuid(s, KVM_CPUID_FEATURES, 0, R_EAX); - env->cpuid_ext4_features &= + env->features[FEAT_C000_0001_EDX] &= kvm_arch_get_supported_cpuid(s, 0xC0000001, 0, R_EDX); } @@ -1619,15 +1639,15 @@ int cpu_x86_register(X86CPU *cpu, const char *cpu_model) object_property_set_int(OBJECT(cpu), def->family, "family", &error); object_property_set_int(OBJECT(cpu), def->model, "model", &error); object_property_set_int(OBJECT(cpu), def->stepping, "stepping", &error); - env->cpuid_features = def->features; - env->cpuid_ext_features = def->ext_features; - env->cpuid_ext2_features = def->ext2_features; - env->cpuid_ext3_features = def->ext3_features; + env->features[FEAT_1_EDX] = def->features[FEAT_1_EDX]; + env->features[FEAT_1_ECX] = def->features[FEAT_1_ECX]; + env->features[FEAT_8000_0001_EDX] = def->features[FEAT_8000_0001_EDX]; + env->features[FEAT_8000_0001_ECX] = def->features[FEAT_8000_0001_ECX]; object_property_set_int(OBJECT(cpu), def->xlevel, "xlevel", &error); - env->cpuid_kvm_features = def->kvm_features; - env->cpuid_svm_features = def->svm_features; - env->cpuid_ext4_features = def->ext4_features; - env->cpuid_7_0_ebx_features = def->cpuid_7_0_ebx_features; + env->features[FEAT_KVM] = def->features[FEAT_KVM]; + env->features[FEAT_SVM] = def->features[FEAT_SVM]; + env->features[FEAT_C000_0001_EDX] = def->features[FEAT_C000_0001_EDX]; + env->features[FEAT_7_0_EBX] = def->features[FEAT_7_0_EBX]; env->cpuid_xlevel2 = def->xlevel2; object_property_set_int(OBJECT(cpu), (int64_t)def->tsc_khz * 1000, "tsc-frequency", &error); @@ -1650,7 +1670,7 @@ error: void cpu_clear_apic_feature(CPUX86State *env) { - env->cpuid_features &= ~CPUID_APIC; + env->features[FEAT_1_EDX] &= ~CPUID_APIC; } #endif /* !CONFIG_USER_ONLY */ @@ -1738,8 +1758,8 @@ void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count, case 1: *eax = env->cpuid_version; *ebx = (env->cpuid_apic_id << 24) | 8 << 8; /* CLFLUSH size in quad words, Linux wants it. */ - *ecx = env->cpuid_ext_features; - *edx = env->cpuid_features; + *ecx = env->features[FEAT_1_ECX]; + *edx = env->features[FEAT_1_EDX]; if (cs->nr_cores * cs->nr_threads > 1) { *ebx |= (cs->nr_cores * cs->nr_threads) << 16; *edx |= 1 << 28; /* HTT bit */ @@ -1807,7 +1827,7 @@ void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count, /* Structured Extended Feature Flags Enumeration Leaf */ if (count == 0) { *eax = 0; /* Maximum ECX value for sub-leaves */ - *ebx = env->cpuid_7_0_ebx_features; /* Feature flags */ + *ebx = env->features[FEAT_7_0_EBX]; /* Feature flags */ *ecx = 0; /* Reserved */ *edx = 0; /* Reserved */ } else { @@ -1842,7 +1862,7 @@ void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count, break; case 0xD: /* Processor Extended State */ - if (!(env->cpuid_ext_features & CPUID_EXT_XSAVE)) { + if (!(env->features[FEAT_1_ECX] & CPUID_EXT_XSAVE)) { *eax = 0; *ebx = 0; *ecx = 0; @@ -1872,8 +1892,8 @@ void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count, case 0x80000001: *eax = env->cpuid_version; *ebx = 0; - *ecx = env->cpuid_ext3_features; - *edx = env->cpuid_ext2_features; + *ecx = env->features[FEAT_8000_0001_ECX]; + *edx = env->features[FEAT_8000_0001_EDX]; /* The Linux kernel checks for the CMPLegacy bit and * discards multiple thread information if it is set. @@ -1914,12 +1934,12 @@ void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count, case 0x80000008: /* virtual & phys address size in low 2 bytes. */ /* XXX: This value must match the one used in the MMU code. */ - if (env->cpuid_ext2_features & CPUID_EXT2_LM) { + if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_LM) { /* 64 bit processor */ /* XXX: The physical address space is limited to 42 bits in exec.c. */ *eax = 0x00003028; /* 48 bits virtual, 40 bits physical */ } else { - if (env->cpuid_features & CPUID_PSE36) { + if (env->features[FEAT_1_EDX] & CPUID_PSE36) { *eax = 0x00000024; /* 36 bits physical */ } else { *eax = 0x00000020; /* 32 bits physical */ @@ -1933,11 +1953,11 @@ void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count, } break; case 0x8000000A: - if (env->cpuid_ext3_features & CPUID_EXT3_SVM) { + if (env->features[FEAT_8000_0001_ECX] & CPUID_EXT3_SVM) { *eax = 0x00000001; /* SVM Revision */ *ebx = 0x00000010; /* nr of ASIDs */ *ecx = 0; - *edx = env->cpuid_svm_features; /* optional features */ + *edx = env->features[FEAT_SVM]; /* optional features */ } else { *eax = 0; *ebx = 0; @@ -1956,7 +1976,7 @@ void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count, *eax = env->cpuid_version; *ebx = 0; *ecx = 0; - *edx = env->cpuid_ext4_features; + *edx = env->features[FEAT_C000_0001_EDX]; break; case 0xC0000002: case 0xC0000003: @@ -2088,7 +2108,7 @@ static void mce_init(X86CPU *cpu) unsigned int bank; if (((cenv->cpuid_version >> 8) & 0xf) >= 6 - && (cenv->cpuid_features & (CPUID_MCE | CPUID_MCA)) == + && (cenv->features[FEAT_1_EDX] & (CPUID_MCE | CPUID_MCA)) == (CPUID_MCE | CPUID_MCA)) { cenv->mcg_cap = MCE_CAP_DEF | MCE_BANKS_DEF; cenv->mcg_ctl = ~(uint64_t)0; @@ -2149,7 +2169,7 @@ void x86_cpu_realize(Object *obj, Error **errp) X86CPU *cpu = X86_CPU(obj); CPUX86State *env = &cpu->env; - if (env->cpuid_7_0_ebx_features && env->cpuid_level < 7) { + if (env->features[FEAT_7_0_EBX] && env->cpuid_level < 7) { env->cpuid_level = 7; } @@ -2159,21 +2179,21 @@ void x86_cpu_realize(Object *obj, Error **errp) if (env->cpuid_vendor1 == CPUID_VENDOR_AMD_1 && env->cpuid_vendor2 == CPUID_VENDOR_AMD_2 && env->cpuid_vendor3 == CPUID_VENDOR_AMD_3) { - env->cpuid_ext2_features &= ~CPUID_EXT2_AMD_ALIASES; - env->cpuid_ext2_features |= (env->cpuid_features + env->features[FEAT_8000_0001_EDX] &= ~CPUID_EXT2_AMD_ALIASES; + env->features[FEAT_8000_0001_EDX] |= (env->features[FEAT_1_EDX] & CPUID_EXT2_AMD_ALIASES); } if (!kvm_enabled()) { - env->cpuid_features &= TCG_FEATURES; - env->cpuid_ext_features &= TCG_EXT_FEATURES; - env->cpuid_ext2_features &= (TCG_EXT2_FEATURES + env->features[FEAT_1_EDX] &= TCG_FEATURES; + env->features[FEAT_1_ECX] &= TCG_EXT_FEATURES; + env->features[FEAT_8000_0001_EDX] &= (TCG_EXT2_FEATURES #ifdef TARGET_X86_64 | CPUID_EXT2_SYSCALL | CPUID_EXT2_LM #endif ); - env->cpuid_ext3_features &= TCG_EXT3_FEATURES; - env->cpuid_svm_features &= TCG_SVM_FEATURES; + env->features[FEAT_8000_0001_ECX] &= TCG_EXT3_FEATURES; + env->features[FEAT_SVM] &= TCG_SVM_FEATURES; } else { #ifdef CONFIG_KVM filter_features_for_kvm(cpu); @@ -2183,7 +2203,7 @@ void x86_cpu_realize(Object *obj, Error **errp) #ifndef CONFIG_USER_ONLY qemu_register_reset(x86_cpu_machine_reset_cb, cpu); - if (cpu->env.cpuid_features & CPUID_APIC || smp_cpus > 1) { + if (cpu->env.features[FEAT_1_EDX] & CPUID_APIC || smp_cpus > 1) { x86_cpu_apic_init(cpu, errp); if (error_is_set(errp)) { return; diff --git a/target-i386/cpu.h b/target-i386/cpu.h index e4a7c50..b202427 100644 --- a/target-i386/cpu.h +++ b/target-i386/cpu.h @@ -817,24 +817,15 @@ typedef struct CPUX86State { uint64_t pat; /* processor features (e.g. for CPUID insn) */ - uint32_t cpuid_level; + uint32_t cpuid_level, cpuid_xlevel, cpuid_xlevel2; + FeatureWordArray features; uint32_t cpuid_vendor1; uint32_t cpuid_vendor2; uint32_t cpuid_vendor3; uint32_t cpuid_version; - uint32_t cpuid_features; - uint32_t cpuid_ext_features; - uint32_t cpuid_xlevel; uint32_t cpuid_model[12]; - uint32_t cpuid_ext2_features; - uint32_t cpuid_ext3_features; uint32_t cpuid_apic_id; int cpuid_vendor_override; - /* Store the results of Centaur's CPUID instructions */ - uint32_t cpuid_xlevel2; - uint32_t cpuid_ext4_features; - /* Flags from CPUID[EAX=7,ECX=0].EBX */ - uint32_t cpuid_7_0_ebx_features; /* MTRRs */ uint64_t mtrr_fixed[11]; @@ -848,8 +839,6 @@ typedef struct CPUX86State { uint8_t soft_interrupt; uint8_t has_error_code; uint32_t sipi_vector; - uint32_t cpuid_kvm_features; - uint32_t cpuid_svm_features; bool tsc_valid; int tsc_khz; void *kvm_xsave_buf; diff --git a/target-i386/helper.c b/target-i386/helper.c index fa622e1..99da02e 100644 --- a/target-i386/helper.c +++ b/target-i386/helper.c @@ -449,7 +449,7 @@ void cpu_x86_update_cr4(CPUX86State *env, uint32_t new_cr4) tlb_flush(env, 1); } /* SSE handling */ - if (!(env->cpuid_features & CPUID_SSE)) { + if (!(env->features[FEAT_1_EDX] & CPUID_SSE)) { new_cr4 &= ~CR4_OSFXSR_MASK; } env->hflags &= ~HF_OSFXSR_MASK; @@ -457,7 +457,7 @@ void cpu_x86_update_cr4(CPUX86State *env, uint32_t new_cr4) env->hflags |= HF_OSFXSR_MASK; } - if (!(env->cpuid_7_0_ebx_features & CPUID_7_0_EBX_SMAP)) { + if (!(env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_SMAP)) { new_cr4 &= ~CR4_SMAP_MASK; } env->hflags &= ~HF_SMAP_MASK; diff --git a/target-i386/kvm.c b/target-i386/kvm.c index 3acff40..11bd906 100644 --- a/target-i386/kvm.c +++ b/target-i386/kvm.c @@ -445,7 +445,7 @@ int kvm_arch_init_vcpu(CPUState *cs) c = &cpuid_data.entries[cpuid_i++]; memset(c, 0, sizeof(*c)); c->function = KVM_CPUID_FEATURES; - c->eax = env->cpuid_kvm_features; + c->eax = env->features[FEAT_KVM]; if (hyperv_enabled()) { memcpy(signature, "Hv#1\0\0\0\0\0\0\0\0", 12); @@ -580,7 +580,8 @@ int kvm_arch_init_vcpu(CPUState *cs) cpuid_data.cpuid.nent = cpuid_i; if (((env->cpuid_version >> 8)&0xF) >= 6 - && (env->cpuid_features&(CPUID_MCE|CPUID_MCA)) == (CPUID_MCE|CPUID_MCA) + && (env->features[FEAT_1_EDX] & (CPUID_MCE|CPUID_MCA)) == + (CPUID_MCE|CPUID_MCA) && kvm_check_extension(cs->kvm_state, KVM_CAP_MCE) > 0) { uint64_t mcg_cap; int banks; diff --git a/target-i386/misc_helper.c b/target-i386/misc_helper.c index 719cacd..4fc4261 100644 --- a/target-i386/misc_helper.c +++ b/target-i386/misc_helper.c @@ -291,22 +291,22 @@ void helper_wrmsr(CPUX86State *env) uint64_t update_mask; update_mask = 0; - if (env->cpuid_ext2_features & CPUID_EXT2_SYSCALL) { + if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_SYSCALL) { update_mask |= MSR_EFER_SCE; } - if (env->cpuid_ext2_features & CPUID_EXT2_LM) { + if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_LM) { update_mask |= MSR_EFER_LME; } - if (env->cpuid_ext2_features & CPUID_EXT2_FFXSR) { + if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_FFXSR) { update_mask |= MSR_EFER_FFXSR; } - if (env->cpuid_ext2_features & CPUID_EXT2_NX) { + if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_NX) { update_mask |= MSR_EFER_NXE; } - if (env->cpuid_ext3_features & CPUID_EXT3_SVM) { + if (env->features[FEAT_8000_0001_ECX] & CPUID_EXT3_SVM) { update_mask |= MSR_EFER_SVME; } - if (env->cpuid_ext2_features & CPUID_EXT2_FFXSR) { + if (env->features[FEAT_8000_0001_EDX] & CPUID_EXT2_FFXSR) { update_mask |= MSR_EFER_FFXSR; } cpu_load_efer(env, (env->efer & ~update_mask) | @@ -513,7 +513,7 @@ void helper_rdmsr(CPUX86State *env) val = env->mtrr_deftype; break; case MSR_MTRRcap: - if (env->cpuid_features & CPUID_MTRR) { + if (env->features[FEAT_1_EDX] & CPUID_MTRR) { val = MSR_MTRRcap_VCNT | MSR_MTRRcap_FIXRANGE_SUPPORT | MSR_MTRRcap_WC_SUPPORTED; } else { diff --git a/target-i386/translate.c b/target-i386/translate.c index 32d21f5..2d45ad4 100644 --- a/target-i386/translate.c +++ b/target-i386/translate.c @@ -7926,11 +7926,11 @@ static inline void gen_intermediate_code_internal(CPUX86State *env, if (flags & HF_SOFTMMU_MASK) { dc->mem_index = (cpu_mmu_index(env) + 1) << 2; } - dc->cpuid_features = env->cpuid_features; - dc->cpuid_ext_features = env->cpuid_ext_features; - dc->cpuid_ext2_features = env->cpuid_ext2_features; - dc->cpuid_ext3_features = env->cpuid_ext3_features; - dc->cpuid_7_0_ebx_features = env->cpuid_7_0_ebx_features; + dc->cpuid_features = env->features[FEAT_1_EDX]; + dc->cpuid_ext_features = env->features[FEAT_1_ECX]; + dc->cpuid_ext2_features = env->features[FEAT_8000_0001_EDX]; + dc->cpuid_ext3_features = env->features[FEAT_8000_0001_ECX]; + dc->cpuid_7_0_ebx_features = env->features[FEAT_7_0_EBX]; #ifdef TARGET_X86_64 dc->lma = (flags >> HF_LMA_SHIFT) & 1; dc->code64 = (flags >> HF_CS64_SHIFT) & 1;
This replaces the feature-bit fields on both X86CPU and x86_def_t structs with an array. With this, we will be able to simplify code that simply does the same operation on all feature words (e.g. kvm_check_features_against_host(), filter_features_for_kvm(), add_flagname_to_bitmaps(), and CPU feature-bit property lookup/registration). This should also help avoid bugs like the ones introduced when we added cpuid_7_0_ebx_features. Today, adding a new feature word to the code requires chaning 5 or 6 different places in the code, and it's very easy to miss a problem when we forget to update one of those parts. See, for example: * The bug solved by commit ffa8c11f0bbf47e1b7a3a62f97bc1da591c6734a; * The fact that check_features_against_host() wasn't checking all feature words as it is supposed to, until very recently. Signed-off-by: Eduardo Habkost <ehabkost@redhat.com> --- This patch was created solely using a sed script and no manual changes, to try to avoid mistakes while converting the code, and make it easier to rebase if necessary. The sed script can be seen at: https://gist.github.com/4271991 --- bsd-user/elfload.c | 2 +- bsd-user/main.c | 4 +- hw/kvm/clock.c | 2 +- linux-user/elfload.c | 2 +- linux-user/main.c | 4 +- target-i386/cpu.c | 592 ++++++++++++++++++++++++---------------------- target-i386/cpu.h | 15 +- target-i386/helper.c | 4 +- target-i386/kvm.c | 5 +- target-i386/misc_helper.c | 14 +- target-i386/translate.c | 10 +- 11 files changed, 332 insertions(+), 322 deletions(-)