# HG changeset patch # User Keir Fraser # Date 1317413803 -3600 # Node ID 2215d7d7382617adbe97831fe35752a027917d1d # Parent d568e2313fd6f055b66a6c3cb2bca6372b77692e X86 MCE: Prevent malicious guest access broken page again To avoid recursive mce. Signed-off-by: Liu, Jinsong Committed-by: Keir Fraser --- a/xen/arch/x86/cpu/mcheck/mce_intel.c +++ b/xen/arch/x86/cpu/mcheck/mce_intel.c @@ -639,6 +639,8 @@ static void intel_memerr_dhandler(int bn /* This is free page */ if (status & PG_OFFLINE_OFFLINED) result->result = MCA_RECOVERED; + else if (status & PG_OFFLINE_AGAIN) + result->result = MCA_NO_ACTION; else if (status & PG_OFFLINE_PENDING) { /* This page has owner */ if (status & PG_OFFLINE_OWNED) { --- a/xen/common/page_alloc.c +++ b/xen/common/page_alloc.c @@ -38,6 +38,7 @@ #include #include #include +#include #include #include #include @@ -704,6 +705,19 @@ int offline_page(unsigned long mfn, int return -EINVAL; } + /* + * NB. When broken page belong to guest, usually hypervisor will + * notify the guest to handle the broken page. However, hypervisor + * need to prevent malicious guest access the broken page again. + * Under such case, hypervisor shutdown guest, preventing recursive mce. + */ + if ( (pg->count_info & PGC_broken) && (owner = page_get_owner(pg)) ) + { + *status = PG_OFFLINE_AGAIN; + domain_shutdown(owner, SHUTDOWN_crash); + return 0; + } + spin_lock(&heap_lock); old_info = mark_page_offline(pg, broken); --- a/xen/include/public/sysctl.h +++ b/xen/include/public/sysctl.h @@ -399,6 +399,7 @@ struct xen_sysctl_page_offline_op { #define PG_OFFLINE_OFFLINED (0x1UL << 1) #define PG_OFFLINE_PENDING (0x1UL << 2) #define PG_OFFLINE_FAILED (0x1UL << 3) +#define PG_OFFLINE_AGAIN (0x1UL << 4) #define PG_ONLINE_FAILED PG_OFFLINE_FAILED #define PG_ONLINE_ONLINED PG_OFFLINE_OFFLINED