Я предполагаю, что вы используете qemu с опцией -cpu
со старой моделью процессора, например Nehalem
. Все примеры кода взяты из исходников qemu 5.0. Я предполагаю, что вы знакомы с инструкцией cpuid
. В target\i386\cpu.c
файле вы можете найти
static X86CPUDefinition builtin_x86_defs[] = {
массив с доступными моделями процессоров. Есть запись для Nehalem:
.name = "Nehalem",
.features[FEAT_1_EDX] =
CPUID_VME | CPUID_SSE2 | CPUID_SSE | CPUID_FXSR | CPUID_MMX |
Например, FEAT_1_EDX
описывает значения, возвращаемые для выполнения процессора 1 в регистре edx для этой модели процессора. Вы также можете увидеть все остальные эмулированные коды.
При запуске qemu с ускорением kvm эти данные отправляются в kvm в функции target\i386\kvm.c
in kvm_arch_init_vcpu
. Эта функция инициализирует cpuid_data
и вызывает kvm_vcpu_ioctl(cs, KVM_SET_CPUID2, &cpuid_data);
.
Идея состоит в том, чтобы выполнить инструкцию cpuid для кодов, которые вы хотите настроить, и добавить доступные биты к соответствующим cpuid_data
записям непосредственно перед отправкой их в kvm.
Например настройку cpuid 1 edx и ecx можно сделать так:
struct kvm_cpuid_entry2 *c = cpuid_find_entry(&cpuid_data.cpuid, 1, 0);
if (c) {
c->ecx |= cpuid1_ecx;
c->edx |= cpuid1_edx;
}
где cpuid1_ecx
и cpuid1_edx
— значения, возвращаемые в ecx и edx при выполнении cpuid 1 на вашем хосте. Поскольку биты функций возвращаются в разных функциях cpuid, вам нужно вручную выбрать, какие из них настроить. Хорошей отправной точкой было бы настроить все записи FEAT_xx, найденные в builtin_x86_defs
, для вашего процессора.
Новые процессоры могут иметь больше записей о функциях, их моделирование сложно, но возможно.
person
nevilad
schedule
19.02.2021