kvm, x86: kvm_mce_inj_* subroutins for templated error injections
PATCH 4/11 kvm, x86: kvm_mce_inj_* subroutins for templated error injections
Refactor codes for maintainability.
Signed-off-by Hidetoshi Seto <[email protected]>
Tested-by Jin Dongming <[email protected]>
--- qemu-kvm.c | 96 ++++++++++++++++++++++++++++++++++++----------------------- 1 files changed, 58 insertions(+), 38 deletions(-)
qemu-kvm.c +58 -38
@@ -1159,6 +1159,51 @@ static void kvm_do_set_mce(CPUState *env, struct kvm_x86_mce *mce, } } } + +static void kvm_mce_inj_srar_dataload (CPUState *env,unsigned long paddr) +{ +struct kvm_x86_mce mce = { + .bank =9 , + .status =MCI_STATUS_VAL |MCI_STATUS_UC |MCI_STATUS_EN + |MCI_STATUS_MISCV |MCI_STATUS_ADDRV |MCI_STATUS_S + |MCI_STATUS_AR |0x134 , + .mcg_status =MCG_STATUS_MCIP |MCG_STATUS_EIPV , + .addr = paddr, + .misc = (MCM_ADDR_PHYS <<6 ) |0xc , + }; + +kvm_do_set_mce (env, &mce,1 ); +} + +static void kvm_mce_inj_srao_memscrub (CPUState *env,unsigned long paddr) +{ +struct kvm_x86_mce mce = { + .bank =9 , + .status =MCI_STATUS_VAL |MCI_STATUS_UC |MCI_STATUS_EN + |MCI_STATUS_MISCV |MCI_STATUS_ADDRV |MCI_STATUS_S + |0xc0 , + .mcg_status =MCG_STATUS_MCIP |MCG_STATUS_RIPV , + .addr = paddr, + .misc = (MCM_ADDR_PHYS <<6 ) |0xc , + }; + +kvm_do_set_mce (env, &mce,1 ); +} + +static void kvm_mce_inj_srao_broadcast (unsigned long paddr) +{ +CPUState *cenv; + +kvm_inject_x86_mce (first_cpu,9 , +MCI_STATUS_VAL |MCI_STATUS_UC |MCI_STATUS_EN + |MCI_STATUS_MISCV |MCI_STATUS_ADDRV |MCI_STATUS_S + |0xc0 , +MCG_STATUS_MCIP |MCG_STATUS_RIPV , paddr, + (MCM_ADDR_PHYS <<6 ) |0xc ,1 ); +for (cenv = first_cpu->next_cpu; cenv !=NULL ; cenv = cenv->next_cpu) +kvm_inject_x86_mce (cenv,1 ,MCI_STATUS_VAL |MCI_STATUS_UC , +MCG_STATUS_MCIP |MCG_STATUS_RIPV ,0 ,0 ,1 ); +}#endif static void sigbus_handler(int n, struct qemu_signalfd_siginfo *siginfo,
@@ -1167,11 +1212,9 @@ static void sigbus_handler(int n, struct qemu_signalfd_siginfo *siginfo,#if defined(KVM_CAP_MCE ) && defined(TARGET_I386 )if ((first_cpu->mcg_cap &MCG_SER_P ) && siginfo->ssi_addr && siginfo->ssi_code ==BUS_MCEERR_AO ) { -uint64_t status;void *vaddr;ram_addr_t ram_addr;unsigned long paddr; -CPUState *cenv;/* Hope we are lucky for AO MCE */ vaddr = (void *)(intptr_t )siginfo->ssi_addr;
@@ -1182,16 +1225,7 @@ static void sigbus_handler(int n, struct qemu_signalfd_siginfo *siginfo, (unsigned long long)siginfo->ssi_addr); return; } - status =MCI_STATUS_VAL |MCI_STATUS_UC |MCI_STATUS_EN - |MCI_STATUS_MISCV |MCI_STATUS_ADDRV |MCI_STATUS_S - |0xc0 ; -kvm_inject_x86_mce (first_cpu,9 , status, -MCG_STATUS_MCIP |MCG_STATUS_RIPV , paddr, - (MCM_ADDR_PHYS <<6 ) |0xc ,1 ); -for (cenv = first_cpu->next_cpu; cenv !=NULL ; cenv = cenv->next_cpu) { -kvm_inject_x86_mce (cenv,1 ,MCI_STATUS_VAL |MCI_STATUS_UC , -MCG_STATUS_MCIP |MCG_STATUS_RIPV ,0 ,0 ,1 ); - } +kvm_mce_inj_srao_broadcast (paddr); } else#endif {
@@ -1333,9 +1367,6 @@ static void flush_queued_work(CPUState *env)static void kvm_on_sigbus (CPUState *env,siginfo_t *siginfo) {#if defined(KVM_CAP_MCE ) && defined(TARGET_I386 ) -struct kvm_x86_mce mce = { - .bank =9 , - };void *vaddr;ram_addr_t ram_addr;unsigned long paddr;
@@ -1343,28 +1374,12 @@ static void kvm_on_sigbus(CPUState *env, siginfo_t *siginfo)if ((env->mcg_cap &MCG_SER_P ) && siginfo->si_addr && (siginfo->si_code ==BUS_MCEERR_AR || siginfo->si_code ==BUS_MCEERR_AO )) { -if (siginfo->si_code ==BUS_MCEERR_AR ) { -/* Fake an Intel architectural Data Load SRAR UCR */ - mce.status =MCI_STATUS_VAL |MCI_STATUS_UC |MCI_STATUS_EN - |MCI_STATUS_MISCV |MCI_STATUS_ADDRV |MCI_STATUS_S - |MCI_STATUS_AR |0x134 ; - mce.misc = (MCM_ADDR_PHYS <<6 ) |0xc ; - mce.mcg_status =MCG_STATUS_MCIP |MCG_STATUS_EIPV ; - }else { -/* -* If there is an MCE excpetion being processed, ignore -* this SRAO MCE -*/ -if (kvm_mce_in_progress (env)) { -return ; - } -/* Fake an Intel architectural Memory scrubbing UCR */ - mce.status =MCI_STATUS_VAL |MCI_STATUS_UC |MCI_STATUS_EN - |MCI_STATUS_MISCV |MCI_STATUS_ADDRV |MCI_STATUS_S - |0xc0 ; - mce.misc = (MCM_ADDR_PHYS <<6 ) |0xc ; - mce.mcg_status =MCG_STATUS_MCIP |MCG_STATUS_RIPV ; +/* +* If there is an MCE excpetion being processed, ignore this SRAO MCE +*/ +if (siginfo->si_code ==BUS_MCEERR_AO &&kvm_mce_in_progress (env)) { +return ; } vaddr = (void *)siginfo->si_addr; if (do_qemu_ram_addr_from_host(vaddr, &ram_addr) ||
@@ -1378,8 +1393,13 @@ static void kvm_on_sigbus(CPUState *env, siginfo_t *siginfo) hardware_memory_error(); } } - mce.addr = paddr; -kvm_do_set_mce (env, &mce,1 ); +if (siginfo->si_code ==BUS_MCEERR_AR ) { +/* Fake an Intel architectural Data Load SRAR UCR */ +kvm_mce_inj_srar_dataload (env, paddr); + }else { +/* Fake an Intel architectural Memory scrubbing UCR */ +kvm_mce_inj_srao_memscrub (env, paddr); + } } else#endif {
Signature · 1 line
1.7.1.1