[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] Re: [Xen-devel] [PATCH 05/11] x86/altp2m: basic data structures and support routines.
On 01/13/2015 03:28 AM, Andrew Cooper wrote: > On 09/01/15 21:26, Ed White wrote: >> Add the basic data structures needed to support alternate p2m's and >> the functions to initialise them and tear them down. >> >> Although Intel hardware can handle 512 EPTP's per hardware thread >> concurrently, only 10 per domain are supported in this patch for >> performance reasons. >> >> The iterator in hap_enable() does need to handle 512, so that is now >> uint16_t. >> >> Signed-off-by: Ed White <edmund.h.white@xxxxxxxxx> >> --- >> xen/arch/x86/hvm/Makefile | 3 +- >> xen/arch/x86/hvm/altp2mhvm.c | 77 +++++++++++++++++++++++++++ >> xen/arch/x86/hvm/hvm.c | 21 ++++++++ >> xen/arch/x86/mm/hap/Makefile | 1 + >> xen/arch/x86/mm/hap/altp2m_hap.c | 66 +++++++++++++++++++++++ >> xen/arch/x86/mm/hap/hap.c | 30 ++++++++++- >> xen/arch/x86/mm/mm-locks.h | 4 ++ >> xen/arch/x86/mm/p2m.c | 102 >> ++++++++++++++++++++++++++++++++++++ >> xen/include/asm-x86/domain.h | 7 +++ >> xen/include/asm-x86/hvm/altp2mhvm.h | 36 +++++++++++++ >> xen/include/asm-x86/hvm/hvm.h | 17 ++++++ >> xen/include/asm-x86/hvm/vcpu.h | 9 ++++ >> xen/include/asm-x86/p2m.h | 22 ++++++++ >> 13 files changed, 393 insertions(+), 2 deletions(-) >> create mode 100644 xen/arch/x86/hvm/altp2mhvm.c >> create mode 100644 xen/arch/x86/mm/hap/altp2m_hap.c >> create mode 100644 xen/include/asm-x86/hvm/altp2mhvm.h >> >> diff --git a/xen/arch/x86/hvm/Makefile b/xen/arch/x86/hvm/Makefile >> index eea5555..5bf8b4f 100644 >> --- a/xen/arch/x86/hvm/Makefile >> +++ b/xen/arch/x86/hvm/Makefile >> @@ -22,4 +22,5 @@ obj-y += vlapic.o >> obj-y += vmsi.o >> obj-y += vpic.o >> obj-y += vpt.o >> -obj-y += vpmu.o >> \ No newline at end of file >> +obj-y += vpmu.o >> +obj-y += altp2mhvm.o >> diff --git a/xen/arch/x86/hvm/altp2mhvm.c b/xen/arch/x86/hvm/altp2mhvm.c >> new file mode 100644 >> index 0000000..fa0af0c >> --- /dev/null >> +++ b/xen/arch/x86/hvm/altp2mhvm.c >> @@ -0,0 +1,77 @@ >> +/* >> + * Alternate p2m HVM >> + * Copyright (c) 2014, Intel Corporation. >> + * >> + * This program is free software; you can redistribute it and/or modify it >> + * under the terms and conditions of the GNU General Public License, >> + * version 2, as published by the Free Software Foundation. >> + * >> + * This program is distributed in the hope it will be useful, but WITHOUT >> + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or >> + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for >> + * more details. >> + * >> + * You should have received a copy of the GNU General Public License along >> with >> + * this program; if not, write to the Free Software Foundation, Inc., 59 >> Temple >> + * Place - Suite 330, Boston, MA 02111-1307 USA. >> + */ >> + >> +#include <asm/hvm/support.h> >> +#include <asm/hvm/hvm.h> >> +#include <asm/p2m.h> >> +#include <asm/hvm/altp2mhvm.h> >> + >> +void >> +altp2mhvm_vcpu_reset(struct vcpu *v) >> +{ >> + struct altp2mvcpu *av = &vcpu_altp2mhvm(v); >> + >> + av->p2midx = 0; >> + av->veinfo = 0; >> + >> + if ( hvm_funcs.ahvm_vcpu_reset ) >> + hvm_funcs.ahvm_vcpu_reset(v); >> +} >> + >> +int >> +altp2mhvm_vcpu_initialise(struct vcpu *v) >> +{ >> + int rc = -EOPNOTSUPP; >> + >> + if ( v != current ) >> + vcpu_pause(v); > > Under what circumstances would a vcpu initialisation happen on current? > All initialisation should happen during domain creation. > A domain never starts in alternate p2m mode, much like it never starts in nestedhvm guest mode. In the in-domain agent case, where the hypercall to enter alternate p2m mode is issued by a vcpu in the target domain, this check is necessary. In my testing, the same domain often enters and leaves alternate p2m mode multiple times, and these initialise and destroy functions are called multiple times. Ed >> + >> + if ( !hvm_funcs.ahvm_vcpu_initialise || >> + (hvm_funcs.ahvm_vcpu_initialise(v) == 0) ) >> + { >> + rc = 0; >> + altp2mhvm_vcpu_reset(v); >> + cpumask_set_cpu(v->vcpu_id, p2m_get_altp2m(v)->dirty_cpumask); >> + >> + ahvm_vcpu_update_eptp(v); >> + } >> + >> + if ( v != current ) >> + vcpu_unpause(v); >> + >> + return rc; >> +} >> + >> +void >> +altp2mhvm_vcpu_destroy(struct vcpu *v) >> +{ >> + if ( v != current ) >> + vcpu_pause(v); >> + >> + if ( hvm_funcs.ahvm_vcpu_destroy ) >> + hvm_funcs.ahvm_vcpu_destroy(v); >> + >> + cpumask_clear_cpu(v->processor, p2m_get_altp2m(v)->dirty_cpumask); >> + altp2mhvm_vcpu_reset(v); >> + >> + ahvm_vcpu_update_eptp(v); >> + ahvm_vcpu_update_vmfunc_ve(v); >> + >> + if ( v != current ) >> + vcpu_unpause(v); >> +} >> diff --git a/xen/arch/x86/hvm/hvm.c b/xen/arch/x86/hvm/hvm.c >> index b89e9d2..e8787cc 100644 >> --- a/xen/arch/x86/hvm/hvm.c >> +++ b/xen/arch/x86/hvm/hvm.c >> @@ -60,6 +60,7 @@ >> #include <asm/hvm/cacheattr.h> >> #include <asm/hvm/trace.h> >> #include <asm/hvm/nestedhvm.h> >> +#include <asm/hvm/altp2mhvm.h> >> #include <asm/mtrr.h> >> #include <asm/apic.h> >> #include <public/sched.h> >> @@ -2290,6 +2291,7 @@ void hvm_vcpu_destroy(struct vcpu *v) >> >> hvm_all_ioreq_servers_remove_vcpu(d, v); >> >> + altp2mhvm_vcpu_destroy(v); >> nestedhvm_vcpu_destroy(v); >> >> free_compat_arg_xlat(v); >> @@ -6377,6 +6379,25 @@ bool_t hvm_altp2m_supported() >> return hvm_funcs.altp2m_supported; >> } >> >> +void ahvm_vcpu_update_eptp(struct vcpu *v) >> +{ >> + if (hvm_funcs.ahvm_vcpu_update_eptp) >> + hvm_funcs.ahvm_vcpu_update_eptp(v); >> +} >> + >> +void ahvm_vcpu_update_vmfunc_ve(struct vcpu *v) >> +{ >> + if (hvm_funcs.ahvm_vcpu_update_vmfunc_ve) >> + hvm_funcs.ahvm_vcpu_update_vmfunc_ve(v); >> +} >> + >> +bool_t ahvm_vcpu_emulate_ve(struct vcpu *v) >> +{ >> + if (hvm_funcs.ahvm_vcpu_emulate_ve) >> + return hvm_funcs.ahvm_vcpu_emulate_ve(v); >> + return 0; >> +} >> + >> /* >> * Local variables: >> * mode: C >> diff --git a/xen/arch/x86/mm/hap/Makefile b/xen/arch/x86/mm/hap/Makefile >> index 68f2bb5..216cd90 100644 >> --- a/xen/arch/x86/mm/hap/Makefile >> +++ b/xen/arch/x86/mm/hap/Makefile >> @@ -4,6 +4,7 @@ obj-y += guest_walk_3level.o >> obj-$(x86_64) += guest_walk_4level.o >> obj-y += nested_hap.o >> obj-y += nested_ept.o >> +obj-y += altp2m_hap.o >> >> guest_walk_%level.o: guest_walk.c Makefile >> $(CC) $(CFLAGS) -DGUEST_PAGING_LEVELS=$* -c $< -o $@ >> diff --git a/xen/arch/x86/mm/hap/altp2m_hap.c >> b/xen/arch/x86/mm/hap/altp2m_hap.c >> new file mode 100644 >> index 0000000..c2cdc42 >> --- /dev/null >> +++ b/xen/arch/x86/mm/hap/altp2m_hap.c >> @@ -0,0 +1,66 @@ >> +/****************************************************************************** >> + * arch/x86/mm/hap/altp2m_hap.c >> + * >> + * Copyright (c) 2014 Intel Corporation. >> + * >> + * This program is free software; you can redistribute it and/or modify >> + * it under the terms of the GNU General Public License as published by >> + * the Free Software Foundation; either version 2 of the License, or >> + * (at your option) any later version. >> + * >> + * This program is distributed in the hope that it will be useful, >> + * but WITHOUT ANY WARRANTY; without even the implied warranty of >> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the >> + * GNU General Public License for more details. >> + * >> + * You should have received a copy of the GNU General Public License >> + * along with this program; if not, write to the Free Software >> + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA >> + */ >> + >> +#include <xen/mem_event.h> >> +#include <xen/event.h> >> +#include <public/mem_event.h> >> +#include <asm/domain.h> >> +#include <asm/page.h> >> +#include <asm/paging.h> >> +#include <asm/p2m.h> >> +#include <asm/mem_sharing.h> >> +#include <asm/hap.h> >> +#include <asm/hvm/support.h> >> + >> +#include "private.h" >> + >> +/* Override macros from asm/page.h to make them work with mfn_t */ >> +#undef mfn_valid >> +#define mfn_valid(_mfn) __mfn_valid(mfn_x(_mfn)) >> +#undef page_to_mfn >> +#define page_to_mfn(_pg) _mfn(__page_to_mfn(_pg)) >> + >> +void >> +altp2m_write_p2m_entry(struct p2m_domain *p2m, unsigned long gfn, >> + l1_pgentry_t *p, l1_pgentry_t new, unsigned int level) >> +{ >> + struct domain *d = p2m->domain; >> + uint32_t old_flags; >> + >> + paging_lock(d); >> + >> + old_flags = l1e_get_flags(*p); >> + safe_write_pte(p, new); >> + >> + if (old_flags & _PAGE_PRESENT) >> + flush_tlb_mask(p2m->dirty_cpumask); >> + >> + paging_unlock(d); >> +} >> + >> +/* >> + * Local variables: >> + * mode: C >> + * c-file-style: "BSD" >> + * c-basic-offset: 4 >> + * tab-width: 4 >> + * indent-tabs-mode: nil >> + * End: >> + */ >> diff --git a/xen/arch/x86/mm/hap/hap.c b/xen/arch/x86/mm/hap/hap.c >> index abf3d7a..8fe0650 100644 >> --- a/xen/arch/x86/mm/hap/hap.c >> +++ b/xen/arch/x86/mm/hap/hap.c >> @@ -439,7 +439,7 @@ void hap_domain_init(struct domain *d) >> int hap_enable(struct domain *d, u32 mode) >> { >> unsigned int old_pages; >> - uint8_t i; >> + uint16_t i; >> int rv = 0; >> >> domain_pause(d); >> @@ -485,6 +485,23 @@ int hap_enable(struct domain *d, u32 mode) >> goto out; >> } >> >> + /* Init alternate p2m data */ >> + if ( (d->arch.altp2m_eptp = alloc_xenheap_page()) == NULL ) > > This memory should be allocated from some domain-accounted pool, > probably the paging pool (d->->arch.paging.alloc_page()). You can use > map_domain_page_global() to get a safe pointer to anchor in > d->arch.altp2m_eptp for hardware. > >> + { >> + rv = -ENOMEM; >> + goto out; >> + } >> + for (i = 0; i < 512; i++) >> + d->arch.altp2m_eptp[i] = ~0ul; >> + >> + for (i = 0; i < MAX_ALTP2M; i++) { >> + rv = p2m_alloc_table(d->arch.altp2m_p2m[i]); >> + if ( rv != 0 ) >> + goto out; >> + } >> + >> + d->arch.altp2m_active = 0; >> + >> /* Now let other users see the new mode */ >> d->arch.paging.mode = mode | PG_HAP_enable; >> >> @@ -497,6 +514,17 @@ void hap_final_teardown(struct domain *d) >> { >> uint8_t i; >> >> + d->arch.altp2m_active = 0; >> + >> + if ( d->arch.altp2m_eptp ) { >> + free_xenheap_page(d->arch.altp2m_eptp); >> + d->arch.altp2m_eptp = NULL; >> + } >> + >> + for (i = 0; i < MAX_ALTP2M; i++) { >> + p2m_teardown(d->arch.altp2m_p2m[i]); >> + } >> + >> /* Destroy nestedp2m's first */ >> for (i = 0; i < MAX_NESTEDP2M; i++) { >> p2m_teardown(d->arch.nested_p2m[i]); >> diff --git a/xen/arch/x86/mm/mm-locks.h b/xen/arch/x86/mm/mm-locks.h >> index 769f7bc..a0faca3 100644 >> --- a/xen/arch/x86/mm/mm-locks.h >> +++ b/xen/arch/x86/mm/mm-locks.h >> @@ -209,6 +209,10 @@ declare_mm_lock(nestedp2m) >> #define nestedp2m_lock(d) mm_lock(nestedp2m, &(d)->arch.nested_p2m_lock) >> #define nestedp2m_unlock(d) mm_unlock(&(d)->arch.nested_p2m_lock) >> >> +declare_mm_lock(altp2m) >> +#define altp2m_lock(d) mm_lock(altp2m, &(d)->arch.altp2m_lock) >> +#define altp2m_unlock(d) mm_unlock(&(d)->arch.altp2m_lock) >> + >> /* P2M lock (per-p2m-table) >> * >> * This protects all queries and updates to the p2m table. >> diff --git a/xen/arch/x86/mm/p2m.c b/xen/arch/x86/mm/p2m.c >> index 49b66fb..3c6049b 100644 >> --- a/xen/arch/x86/mm/p2m.c >> +++ b/xen/arch/x86/mm/p2m.c >> @@ -35,6 +35,7 @@ >> #include <asm/hvm/vmx/vmx.h> /* ept_p2m_init() */ >> #include <asm/mem_sharing.h> >> #include <asm/hvm/nestedhvm.h> >> +#include <asm/hvm/altp2mhvm.h> >> #include <asm/hvm/svm/amd-iommu-proto.h> >> #include <xsm/xsm.h> >> >> @@ -182,6 +183,44 @@ static void p2m_teardown_nestedp2m(struct domain *d) >> } >> } >> >> +static void p2m_teardown_altp2m(struct domain *d); >> + >> +static int p2m_init_altp2m(struct domain *d) >> +{ >> + uint8_t i; >> + struct p2m_domain *p2m; >> + >> + mm_lock_init(&d->arch.altp2m_lock); >> + for (i = 0; i < MAX_ALTP2M; i++) >> + { >> + d->arch.altp2m_p2m[i] = p2m = p2m_init_one(d); >> + if ( p2m == NULL ) >> + { >> + p2m_teardown_altp2m(d); >> + return -ENOMEM; >> + } >> + p2m->write_p2m_entry = altp2m_write_p2m_entry; >> + p2m->alternate = 1; >> + } >> + >> + return 0; >> +} >> + >> +static void p2m_teardown_altp2m(struct domain *d) >> +{ >> + uint8_t i; >> + struct p2m_domain *p2m; >> + >> + for (i = 0; i < MAX_ALTP2M; i++) >> + { >> + if ( !d->arch.altp2m_p2m[i] ) >> + continue; >> + p2m = d->arch.altp2m_p2m[i]; >> + p2m_free_one(p2m); >> + d->arch.altp2m_p2m[i] = NULL; >> + } >> +} >> + >> int p2m_init(struct domain *d) >> { >> int rc; >> @@ -195,7 +234,14 @@ int p2m_init(struct domain *d) >> * (p2m_init runs too early for HVM_PARAM_* options) */ >> rc = p2m_init_nestedp2m(d); >> if ( rc ) >> + { >> p2m_teardown_hostp2m(d); >> + return rc; >> + } >> + >> + rc = p2m_init_altp2m(d); >> + if ( rc ) >> + p2m_teardown_altp2m(d); >> >> return rc; >> } >> @@ -1891,6 +1937,62 @@ int unmap_mmio_regions(struct domain *d, >> return err; >> } >> >> +bool_t p2m_find_altp2m_by_eptp(struct domain *d, uint64_t eptp, unsigned >> long *idx) >> +{ >> + struct p2m_domain *p2m; >> + struct ept_data *ept; >> + bool_t rc = 0; >> + uint16_t i; >> + >> + altp2m_lock(d); >> + >> + for ( i = 0; i < MAX_ALTP2M; i++ ) >> + { >> + if ( d->arch.altp2m_eptp[i] == ~0ul ) >> + continue; >> + >> + p2m = d->arch.altp2m_p2m[i]; >> + ept = &p2m->ept; >> + >> + if ( eptp != ept_get_eptp(ept) ) >> + continue; >> + >> + *idx = i; >> + rc = 1; >> + >> + break; >> + } >> + >> + altp2m_unlock(d); >> + return rc; >> +} >> + >> +bool_t p2m_switch_vcpu_altp2m_by_id(struct vcpu *v, uint16_t idx) >> +{ >> + struct domain *d = v->domain; >> + bool_t rc = 0; >> + >> + if ( idx > MAX_ALTP2M ) >> + return rc; >> + >> + altp2m_lock(d); >> + >> + if ( d->arch.altp2m_eptp[idx] != ~0ul ) >> + { >> + if ( idx != vcpu_altp2mhvm(v).p2midx ) >> + { >> + cpumask_clear_cpu(v->vcpu_id, p2m_get_altp2m(v)->dirty_cpumask); >> + vcpu_altp2mhvm(v).p2midx = idx; >> + cpumask_set_cpu(v->vcpu_id, p2m_get_altp2m(v)->dirty_cpumask); >> + ahvm_vcpu_update_eptp(v); >> + } >> + rc = 1; >> + } >> + >> + altp2m_unlock(d); >> + return rc; >> +} >> + >> /*** Audit ***/ >> >> #if P2M_AUDIT >> diff --git a/xen/include/asm-x86/domain.h b/xen/include/asm-x86/domain.h >> index 6a77a93..a0e9e90 100644 >> --- a/xen/include/asm-x86/domain.h >> +++ b/xen/include/asm-x86/domain.h >> @@ -230,6 +230,7 @@ struct paging_vcpu { >> typedef xen_domctl_cpuid_t cpuid_input_t; >> >> #define MAX_NESTEDP2M 10 >> +#define MAX_ALTP2M 10 >> struct p2m_domain; >> struct time_scale { >> int shift; >> @@ -274,6 +275,12 @@ struct arch_domain >> struct p2m_domain *nested_p2m[MAX_NESTEDP2M]; >> mm_lock_t nested_p2m_lock; >> >> + /* altp2m: allow multiple copies of host p2m */ >> + bool_t altp2m_active; >> + struct p2m_domain *altp2m_p2m[MAX_ALTP2M]; >> + mm_lock_t altp2m_lock; >> + uint64_t *altp2m_eptp; >> + >> /* NB. protected by d->event_lock and by irq_desc[irq].lock */ >> struct radix_tree_root irq_pirq; >> >> diff --git a/xen/include/asm-x86/hvm/altp2mhvm.h >> b/xen/include/asm-x86/hvm/altp2mhvm.h >> new file mode 100644 >> index 0000000..919986e >> --- /dev/null >> +++ b/xen/include/asm-x86/hvm/altp2mhvm.h >> @@ -0,0 +1,36 @@ >> +/* >> + * Alternate p2m HVM >> + * Copyright (c) 2014, Intel Corporation. >> + * >> + * This program is free software; you can redistribute it and/or modify it >> + * under the terms and conditions of the GNU General Public License, >> + * version 2, as published by the Free Software Foundation. >> + * >> + * This program is distributed in the hope it will be useful, but WITHOUT >> + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or >> + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for >> + * more details. >> + * >> + * You should have received a copy of the GNU General Public License along >> with >> + * this program; if not, write to the Free Software Foundation, Inc., 59 >> Temple >> + * Place - Suite 330, Boston, MA 02111-1307 USA. >> + */ >> + >> +#ifndef _HVM_ALTP2M_H >> +#define _HVM_ALTP2M_H >> + >> +#include <xen/types.h> /* for uintNN_t */ >> +#include <xen/sched.h> /* for struct vcpu, struct domain */ >> +#include <asm/hvm/vcpu.h> /* for vcpu_altp2mhvm */ >> + >> +/* Alternate p2m HVM on/off per domain */ >> +#define altp2mhvm_active(d) \ >> + d->arch.altp2m_active > > static inline bool_t altp2mhvm_active(const struct domain *d) > { > return d->arch.altp2m_active; > } > > Type systems are a nice. We should use them where possible. > >> + >> +/* Alternate p2m VCPU */ >> +int altp2mhvm_vcpu_initialise(struct vcpu *v); >> +void altp2mhvm_vcpu_destroy(struct vcpu *v); >> +void altp2mhvm_vcpu_reset(struct vcpu *v); >> + >> +#endif /* _HVM_ALTP2M_H */ >> + >> diff --git a/xen/include/asm-x86/hvm/hvm.h b/xen/include/asm-x86/hvm/hvm.h >> index 7115a68..32d1d02 100644 >> --- a/xen/include/asm-x86/hvm/hvm.h >> +++ b/xen/include/asm-x86/hvm/hvm.h >> @@ -210,6 +210,14 @@ struct hvm_function_table { >> uint32_t *ecx, uint32_t *edx); >> >> void (*enable_msr_exit_interception)(struct domain *d); >> + >> + /* Alternate p2m */ >> + int (*ahvm_vcpu_initialise)(struct vcpu *v); >> + void (*ahvm_vcpu_destroy)(struct vcpu *v); >> + int (*ahvm_vcpu_reset)(struct vcpu *v); >> + void (*ahvm_vcpu_update_eptp)(struct vcpu *v); >> + void (*ahvm_vcpu_update_vmfunc_ve)(struct vcpu *v); >> + bool_t (*ahvm_vcpu_emulate_ve)(struct vcpu *v); >> }; >> >> extern struct hvm_function_table hvm_funcs; >> @@ -531,6 +539,15 @@ extern bool_t opt_hvm_fep; >> #define opt_hvm_fep 0 >> #endif >> >> +/* updates the current EPTP in VMCS */ >> +void ahvm_vcpu_update_eptp(struct vcpu *v); >> + >> +/* updates VMCS fields related to VMFUNC and #VE */ >> +void ahvm_vcpu_update_vmfunc_ve(struct vcpu *v); >> + >> +/* emulates #VE */ >> +bool_t ahvm_vcpu_emulate_ve(struct vcpu *v); > > These should be added in the patch which introduces them. > >> + >> #endif /* __ASM_X86_HVM_HVM_H__ */ >> >> /* >> diff --git a/xen/include/asm-x86/hvm/vcpu.h b/xen/include/asm-x86/hvm/vcpu.h >> index 01e0665..9302d40 100644 >> --- a/xen/include/asm-x86/hvm/vcpu.h >> +++ b/xen/include/asm-x86/hvm/vcpu.h >> @@ -118,6 +118,13 @@ struct nestedvcpu { >> >> #define vcpu_nestedhvm(v) ((v)->arch.hvm_vcpu.nvcpu) >> >> +struct altp2mvcpu { >> + uint16_t p2midx ; /* alternate p2m index */ > > Stray space. > >> + uint64_t veinfo; /* #VE information page guest pfn */ >> +}; >> + >> +#define vcpu_altp2mhvm(v) ((v)->arch.hvm_vcpu.avcpu) > > static inline as well please. > > ~Andrew > >> + >> struct hvm_vcpu { >> /* Guest control-register and EFER values, just as the guest sees them. >> */ >> unsigned long guest_cr[5]; >> @@ -163,6 +170,8 @@ struct hvm_vcpu { >> >> struct nestedvcpu nvcpu; >> >> + struct altp2mvcpu avcpu; >> + >> struct mtrr_state mtrr; >> u64 pat_cr; >> >> diff --git a/xen/include/asm-x86/p2m.h b/xen/include/asm-x86/p2m.h >> index 8193901..9fb5ba0 100644 >> --- a/xen/include/asm-x86/p2m.h >> +++ b/xen/include/asm-x86/p2m.h >> @@ -688,6 +688,28 @@ void nestedp2m_write_p2m_entry(struct p2m_domain *p2m, >> unsigned long gfn, >> l1_pgentry_t *p, l1_pgentry_t new, unsigned int level); >> >> /* >> + * Alternate p2m: shadow p2m tables used for alternate memory views >> + */ >> + >> +void altp2m_write_p2m_entry(struct p2m_domain *p2m, unsigned long gfn, >> + l1_pgentry_t *p, l1_pgentry_t new, unsigned int level); >> + >> +/* get current alternate p2m table */ >> +static inline struct p2m_domain *p2m_get_altp2m(struct vcpu *v) >> +{ >> + struct domain *d = v->domain; >> + uint16_t index = vcpu_altp2mhvm(v).p2midx; >> + >> + return d->arch.altp2m_p2m[index]; >> +} >> + >> +/* Locate an alternate p2m by its EPTP */ >> +bool_t p2m_find_altp2m_by_eptp(struct domain *d, uint64_t eptp, unsigned >> long *idx); >> + >> +/* Switch alternate p2m for a single vcpu */ >> +bool_t p2m_switch_vcpu_altp2m_by_id(struct vcpu *v, uint16_t idx); >> + >> +/* >> * p2m type to IOMMU flags >> */ >> static inline unsigned int p2m_get_iommu_flags(p2m_type_t p2mt) > > _______________________________________________ Xen-devel mailing list Xen-devel@xxxxxxxxxxxxx http://lists.xen.org/xen-devel
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |