Keir Fraser wrote:
On 10/9/07 13:03, "Ben Guthro" <bguthro@xxxxxxxxxxxxxxx> wrote:
15185-1f8fb764f843
http://xenbits.xensource.com/xen-unstable.hg?rev/1f8fb764f843
I'm inclined not to backport this one.
Attached is the exported changeset, series file, and updated patch
15473, should you change your mind.
# HG changeset patch
# User kfraser@xxxxxxxxxxxxxxxxxxxxx
# Node ID 300d1effb792700ad231a9627443be4158b832a8
# Parent d6078c9423555d7ada248594114ff041893bade6
Use short name format when reference to vcpu vmx union member.
Signed-off-by: Xin Li <xin.b.li@xxxxxxxxx>
xen-unstable changeset: 15473:300d1effb792700ad231a9627443be4158b832a8
xen-unstable date: Fri Jul 06 14:36:34 2007 +0100
diff -r 3df9bf768ba3 xen/arch/x86/hvm/vmx/intr.c
--- a/xen/arch/x86/hvm/vmx/intr.c Mon Sep 10 09:13:38 2007 -0400
+++ b/xen/arch/x86/hvm/vmx/intr.c Mon Sep 10 09:13:38 2007 -0400
@@ -73,7 +73,7 @@
static void enable_irq_window(struct vcpu *v)
{
- u32 *cpu_exec_control = &v->arch.hvm_vcpu.u.vmx.exec_control;
+ u32 *cpu_exec_control = &v->arch.hvm_vmx.exec_control;
if ( !(*cpu_exec_control & CPU_BASED_VIRTUAL_INTR_PENDING) )
{
diff -r 3df9bf768ba3 xen/arch/x86/hvm/vmx/vmcs.c
--- a/xen/arch/x86/hvm/vmx/vmcs.c Mon Sep 10 09:13:38 2007 -0400
+++ b/xen/arch/x86/hvm/vmx/vmcs.c Mon Sep 10 09:15:23 2007 -0400
@@ -316,7 +316,7 @@ static void construct_vmcs(struct vcpu *
__vmwrite(VM_EXIT_CONTROLS, vmx_vmexit_control);
__vmwrite(VM_ENTRY_CONTROLS, vmx_vmentry_control);
__vmwrite(CPU_BASED_VM_EXEC_CONTROL, vmx_cpu_based_exec_control);
- v->arch.hvm_vcpu.u.vmx.exec_control = vmx_cpu_based_exec_control;
+ v->arch.hvm_vmx.exec_control = vmx_cpu_based_exec_control;
if ( vmx_cpu_based_exec_control & ACTIVATE_SECONDARY_CONTROLS )
__vmwrite(SECONDARY_VM_EXEC_CONTROL, vmx_secondary_exec_control);
diff -r 3df9bf768ba3 xen/arch/x86/hvm/vmx/vmx.c
--- a/xen/arch/x86/hvm/vmx/vmx.c Mon Sep 10 09:13:38 2007 -0400
+++ b/xen/arch/x86/hvm/vmx/vmx.c Mon Sep 10 09:13:38 2007 -0400
@@ -417,8 +417,8 @@ static inline void vmx_save_dr(struct vc
/* Clear the DR dirty flag and re-enable intercepts for DR accesses. */
v->arch.hvm_vcpu.flag_dr_dirty = 0;
- v->arch.hvm_vcpu.u.vmx.exec_control |= CPU_BASED_MOV_DR_EXITING;
- __vmwrite(CPU_BASED_VM_EXEC_CONTROL, v->arch.hvm_vcpu.u.vmx.exec_control);
+ v->arch.hvm_vmx.exec_control |= CPU_BASED_MOV_DR_EXITING;
+ __vmwrite(CPU_BASED_VM_EXEC_CONTROL, v->arch.hvm_vmx.exec_control);
savedebug(&v->arch.guest_context, 0);
savedebug(&v->arch.guest_context, 1);
@@ -1410,9 +1410,9 @@ static void vmx_dr_access(unsigned long
__restore_debug_registers(v);
/* Allow guest direct access to DR registers */
- v->arch.hvm_vcpu.u.vmx.exec_control &= ~CPU_BASED_MOV_DR_EXITING;
+ v->arch.hvm_vmx.exec_control &= ~CPU_BASED_MOV_DR_EXITING;
__vmwrite(CPU_BASED_VM_EXEC_CONTROL,
- v->arch.hvm_vcpu.u.vmx.exec_control);
+ v->arch.hvm_vmx.exec_control);
}
/*
@@ -2967,15 +2967,15 @@ asmlinkage void vmx_vmexit_handler(struc
break;
case EXIT_REASON_PENDING_VIRT_INTR:
/* Disable the interrupt window. */
- v->arch.hvm_vcpu.u.vmx.exec_control &= ~CPU_BASED_VIRTUAL_INTR_PENDING;
+ v->arch.hvm_vmx.exec_control &= ~CPU_BASED_VIRTUAL_INTR_PENDING;
__vmwrite(CPU_BASED_VM_EXEC_CONTROL,
- v->arch.hvm_vcpu.u.vmx.exec_control);
+ v->arch.hvm_vmx.exec_control);
break;
case EXIT_REASON_PENDING_VIRT_NMI:
/* Disable the NMI window. */
- v->arch.hvm_vcpu.u.vmx.exec_control &= ~CPU_BASED_VIRTUAL_NMI_PENDING;
+ v->arch.hvm_vmx.exec_control &= ~CPU_BASED_VIRTUAL_NMI_PENDING;
__vmwrite(CPU_BASED_VM_EXEC_CONTROL,
- v->arch.hvm_vcpu.u.vmx.exec_control);
+ v->arch.hvm_vmx.exec_control);
break;
case EXIT_REASON_TASK_SWITCH:
goto exit_and_crash;
15023-6e597e529fea
15035-23c4790512db
15038-e19ddfa781c5
15039-60240a72e2b2
15043-759d924af6d8
15044-03a13457d993
15045-5f6da38ff828
15046-e527b4ff1948
15048-e33cce8fa400
15049-174995130550
15051-384a29655270
15052-65ce4866d20b
15053-3ecf51689671
15056-a605044ecb33
15057-75b4c7cb007d
15058-3581a77791e3
15061-05ea0d79a92f
15062-b2adb797900a
15063-807f374e720d
15064-eb027b704dc5
15065-f4390e34ad12
15066-9e9c09c75110
15067-c027880b50b4
15068-dc4324d3fbb0
15069-cb006eecd6f5
15070-fbce94a9feaa
15072-d4a0706d6747
15073-e1f43038f1d8
15074-5c7a1e3abd54
15075-5efb46bfbcac
15076-9ec165fa8128
15077-711bfe07999b
15078-6145e5508d6b
15079-11a97dca57aa
15080-089696e0c603
15082-0fd2bf14f38a
15083-b9da101ed945
15128-f6928d636999
15130-a40967e39652
15132-17f6163ae930
15133-46095d5a59a9
15134-96915ca8d5f2
15135-e49b110cbb4a
15136-cc60c18247f1
15137-297d98f057e8
15138-471478a1b89e
15139-020530a6ff5c
15141-12a12637af46
15142-acee9e2c6f8b
15143-2623444e6d33
15144-f38f7f583f33
15147-36959baf05c0
15148-7ff65f888804
15149-8fcefab1d63b
15150-fe0499f6235c
15151-6223d154e55f
15152-853853686147
15153-f07c1bb86d6c
15154-965bf43c9f11
15155-1fde9ebb8019
15156-6a4af9502b4d
15157-3ef4a4d82130
15158-588bd40872ec
15160-21f1a7a7ea30
15161-e046da853ffc
15162-d1cce5bafe28
15163-16e376ed5638
15165-4730ec3d5ab3
15166-546044bfd49f
15167-9073caff4b63
15168-a717cb2fac90
15170-ca62b4b4f762
15171-cf3cf0d1b175
15173-88e41a91301c
15174-a00d55b15327
15175-c49987e71dae
15176-f0772865c85a
15177-33242afccb32
15178-1bad5a932df5
15179-152dc0d812b2
15183-63211a8027fa
xen-unstable.hg-15185.patch
15188-ae073ca6eb76
15189-2d7d33ac982a
15190-c9d66baad22b
15193-d1d5ceb3c3ff
15194-4c2b8ca4842c
15197-2d3034d0b36b
15199-13eca4bf2c69
15200-bd3d6b4c52ec
15207-c388a2ff1b8e
15208-6c636bd3f874
15209-20ccb03e738d
15214-5710c94e6539
15216-6f13c3be08fa
15217-7a16a499152c
15221-4f05a587cb6b
15222-0feaf2fc75d3
15223-c5cf3942b5da
15226-736e7cf0a3a5
15227-f5a71c9771a8
15228-677731eb734d
15232-d47415adf384
15233-3a413f011b8f
15235-a7601de2f733
15236-56bab6f498ac
15237-a5ae31a91b10
15238-345ae2e61ba0
15239-656b8175f4f2
15240-55230846b2f4
15243-3cc79ef896a2
15244-91aeaf000ca2
15245-608ddb14259b
15247-ac9d3bcc7a78
15248-7eeddd787d2f
15249-93f77a5a8437
15250-a43a03d53781
15251-6f06bd06ef47
15253-ebe4140fe4f8
15255-3d5f39c610ad
15256-2c8c6ca1296b
15258-bd94f75fe469
15259-35e38c9048c8
15261-112703751b19
15262-9766af047b6c
15263-feeca16435bf
15264-e1c54c14220a
15266-b515e66234e8
15267-be33028fcda5
15268-699f0c429620
15269-c56ebab69b84
15270-0f9d683a83ed
15272-30449e0e0a64
15273-7f9362a8ae3d
15274-ffdbe8aebde2
15275-b643179d7452
15276-4d8381679606
15277-912f7e312ec2
15278-a0c0c7efffca
15279-80eb95dc0dd9
15280-80577631fb87
15281-356588dda4bc
15283-e08cbd487414
15284-276b48771f1e
15285-b4c16658ca30
15287-ba61ec7df632
15288-f1ba2e652724
15289-8ad38aaaeb89
15290-56548d9a7ba7
15291-1feb91894e11
15373-58b6223074af
15374-b1eb43f94a3a
15375-342c85cfd00b
15376-c3f280acf41a
15377-75d82009ec70
15378-5794f9b80c3f
15379-8eaee9ef472f
15380-07688f8f5394
15381-f1ca92bf7e0f
15382-cb747a35e057
15383-896b536d66c9
15386-fb5077ecf9a4
15387-739d698986e9
15389-07be0266f6d8
15390-69658f935cc7
15391-fe3df33e2761
15393-63077ce6a7dc
15394-168b143a1a88
15395-3187ffc5272c
15396-2805246f6cac
15398-499bab040137
15399-45a44a9cbe8d
15400-005dd6b1cf8e
15401-79b180596baf
15402-799b3e4bfeac
15404-f50f0ec7dd2c
15406-296fd2598e00
15407-6310aebd34a6
15408-cf846f4d756f
15409-11bf94b2d51a
15410-a83632dfbb28
15411-5ec34f7f31ab
15412-acb7aa72fac7
15413-899a44cb6ef6
15414-3cf5052ba5e5
15415-04d4b7b6f5b7
15416-b35b8053012e
15417-015d9abeacfb
15418-3f76b2f76c2a
15420-b14bbd41e9dc
15421-c72a93cbcedb
15422-16f35bea00f8
15423-5eec9a8825d4
15424-87d34c8c2fe1
15427-4ab9e4bbd61b
15429-b370047d0fa0
15431-3362de397f1e
15432-d0608ecb56bc
15433-a5360bf18668
15434-b377a102f0eb
15435-ab95b9764b20
15436-2cdf8fef8d93
15437-713bac7cba46
15439-a3a0202af8a4
15441-6e8199e555a6
15442-7a31e37fec9e
15443-5d7160564381
15445-182446677b6b
15446-f85252ce203e
15449-1e04c4be12aa
15450-b528cb182cc7
15451-296ffa18524a
15453-0900fb1a3693
15454-83cbda5c1e1b
15455-c192e3241eb7
15456-eb2b7ce05f97
15457-08bcc54aee8e
15458-8adfd96f62ae
15459-842e085dbb77
15460-b8e8061c5a98
15461-0528bc25c404
15462-eb71f258e855
15463-56da8753ba8d
15464-f1b62eb7f8be
15465-9fa9346e1c70
15469-936aa542053d
15470-b01225c94f83
15472-d6078c942355
15473-300d1effb792
15474-2dee920e0fd7
15475-57398acc1480
15476-f20ee5bc9d28
15477-3196b63a7301
15478-05331a29f3cb
15480-daa07db3ca84
15483-eaf3aa32fa88
15497-8528da5be577
15498-41c8284cfc0c
15499-50c18666d660
15500-259bb15b2d1e
15501-107b9bde5e4d
15502-99143d572521
15503-27e993c80ceb
15508-ecb89c6ce615
15509-646ec1f2b41f
15510-5e8eb0cf2daf
15511-83fd4ad219cd
15522-0eec072e870a
15524-26eef8426110
15528-637ff26be6ff
15535-c6491ed12f84
15583-b27add01a929
15584-48c8244c47c7
15588-0aa2a954a6d1
15590-f479595a3c5c
15592-a17f20a0fd19
15595-1158b6115b14
15596-d99903a98ad0
15605-4721e9d836dd
15606-4197a1aad70b
15621-f85acff5bef5
15637-eff24408830c
15643-68260372b6da
15644-3ec3e2840a29
15660-66055f773d19
15661-7c5c3aa858cc
15671-0c79a9414f8d
15673-f343d3c16dcc
15674-07364f8574b8
15684-52e5c110aadb
15686-0120cca78435
15692-b82e6818fb31
15693-c229802cedbb
fix-qemu-dm-event-loop-crash
linux-30-45dfe4cfc5ef
linux-31-396dfc842377
linux-32-dd861cfb5d1a
linux-34-0301c1fd8c0d
linux-35-85b046c1da18
linux-42-c09686d2bbff
linux-47-33c3009e73ec
linux-65-87bb8705768a
linux-66-496e3157a35c
linux-68-cadc6d58a9e6
linux-74-cb50d25a9468
linux-78-0be610b725fa
linux-80-4a284f968015
linux-81-cb040341e05a
linux-82-11483a00c017
linux-93-08cf42135056
linux-94-d36fd1c5db16
linux-99-f15643dab1ca
linux-100-5a4e93508aa0
linux-101-5684370b1c4d
linux-103-a70de77dd8d3
linux-104-06cd871a5a98
linux-105-b3c2f84be0bb
linux-106-9942e31a3ec5
linux-136-34ebf92ad28d
linux-137-41918416db51
linux-141-5e294e29a43e
linux-144-d88e59a7334a
linux-145-3b0bce92b2f2
linux-146-726cd201f4cd
linux-147-88a17da7f336
linux-148-667228bf8fc5
linux-150-09c88868e344
linux-151-1372bc676080
linux-152-8d5ae51a09a6
linux-156-d2f9b7e36231
linux-157-877c2e42a701
linux-190-f30b59f550c2
15706-359707941ae8
15712-b55fe44438bc
15713-db21f714d37f
15714-3876b4e7cc0a
15717-8c77ae93f982
15719-c362bcee8047
15720-f2649861d594
15721-01c721fddb90
15724-fdffab15499d
15725-ef79bf6f0142
15730-256160ff19b7
15733-cd511c380e03
15734-2ece8ff05ce7
15735-458e8b37aec8
15773-f279d776fcb0
15778-2aee2e4eacc8
15779-505021d029eb
15780-7f53312a3297
15781-8e3abd893835
15782-8e9ec8711efa
15785-747b71c8c4a8
15786-828e1df114d4
15788-c868eab6c99b
15789-2eb38cefdcd9
15790-b485d8d7347a
15791-c398dad9d50a
15799-3738840029b4
15800-fba9884685fb
15801-b3689eb59c5e
15802-d032a17aced2
15807-0f196e11a143
15815-2f13d0f2b07c
15817-ca0938180509
15830-32f331858d75
15832-f779ee15c553
15833-05950e909ba6
linux-191-1e2284d885fb
linux-192-5ce5bd383ea9
diff -r 8f147a735faf xen/arch/x86/hvm/hvm.c
--- a/xen/arch/x86/hvm/hvm.c Fri Aug 17 14:47:30 2007 -0400
+++ b/xen/arch/x86/hvm/hvm.c Fri Aug 17 14:47:32 2007 -0400
@@ -224,6 +224,7 @@ int hvm_domain_initialise(struct domain
spin_lock_init(&d->arch.hvm_domain.pbuf_lock);
spin_lock_init(&d->arch.hvm_domain.irq_lock);
+ spin_lock_init(&d->arch.hvm_domain.vapic_access_lock);
rc = paging_enable(d, PG_refcounts|PG_translate|PG_external);
if ( rc != 0 )
diff -r 8f147a735faf xen/arch/x86/hvm/vlapic.c
--- a/xen/arch/x86/hvm/vlapic.c Fri Aug 17 14:47:30 2007 -0400
+++ b/xen/arch/x86/hvm/vlapic.c Fri Aug 17 14:47:32 2007 -0400
@@ -79,8 +79,6 @@ static unsigned int vlapic_lvt_mask[VLAP
#define vlapic_lvtt_period(vlapic) \
(vlapic_get_reg(vlapic, APIC_LVTT) & APIC_LVT_TIMER_PERIODIC)
-#define vlapic_base_address(vlapic) \
- (vlapic->hw.apic_base_msr & MSR_IA32_APICBASE_BASE)
/*
* Generic APIC bitmap vector update & search routines.
diff -r 8f147a735faf xen/arch/x86/hvm/vmx/intr.c
--- a/xen/arch/x86/hvm/vmx/intr.c Fri Aug 17 14:47:30 2007 -0400
+++ b/xen/arch/x86/hvm/vmx/intr.c Fri Aug 17 14:47:32 2007 -0400
@@ -67,13 +67,17 @@ static inline int is_interruptibility_st
return __vmread(GUEST_INTERRUPTIBILITY_INFO);
}
-#ifdef __x86_64__
static void update_tpr_threshold(struct vlapic *vlapic)
{
int max_irr, tpr;
if ( !cpu_has_vmx_tpr_shadow )
return;
+
+#ifdef __i386__
+ if ( !vlapic->mmap_vtpr_enabled )
+ return;
+#endif
if ( !vlapic_enabled(vlapic) ||
((max_irr = vlapic_find_highest_irr(vlapic)) == -1) )
@@ -85,9 +89,6 @@ static void update_tpr_threshold(struct
tpr = vlapic_get_reg(vlapic, APIC_TASKPRI) & 0xF0;
__vmwrite(TPR_THRESHOLD, (max_irr > tpr) ? (tpr >> 4) : (max_irr >> 4));
}
-#else
-#define update_tpr_threshold(v) ((void)0)
-#endif
asmlinkage void vmx_intr_assist(void)
{
diff -r 8f147a735faf xen/arch/x86/hvm/vmx/vmcs.c
--- a/xen/arch/x86/hvm/vmx/vmcs.c Fri Aug 17 14:47:30 2007 -0400
+++ b/xen/arch/x86/hvm/vmx/vmcs.c Fri Aug 17 14:47:32 2007 -0400
@@ -40,6 +40,7 @@
/* Dynamic (run-time adjusted) execution control flags. */
u32 vmx_pin_based_exec_control __read_mostly;
u32 vmx_cpu_based_exec_control __read_mostly;
+u32 vmx_secondary_exec_control __read_mostly;
u32 vmx_vmexit_control __read_mostly;
u32 vmx_vmentry_control __read_mostly;
@@ -59,12 +60,16 @@ static u32 adjust_vmx_controls(u32 ctl_m
return ctl;
}
+
+#define vmx_has_secondary_exec_ctls \
+ (_vmx_cpu_based_exec_control & ACTIVATE_SECONDARY_CONTROLS)
void vmx_init_vmcs_config(void)
{
u32 vmx_msr_low, vmx_msr_high, min, opt;
u32 _vmx_pin_based_exec_control;
u32 _vmx_cpu_based_exec_control;
+ u32 _vmx_secondary_exec_control = 0;
u32 _vmx_vmexit_control;
u32 _vmx_vmentry_control;
@@ -80,9 +85,8 @@ void vmx_init_vmcs_config(void)
CPU_BASED_ACTIVATE_IO_BITMAP |
CPU_BASED_USE_TSC_OFFSETING);
opt = CPU_BASED_ACTIVATE_MSR_BITMAP;
-#ifdef __x86_64__
opt |= CPU_BASED_TPR_SHADOW;
-#endif
+ opt |= ACTIVATE_SECONDARY_CONTROLS;
_vmx_cpu_based_exec_control = adjust_vmx_controls(
min, opt, MSR_IA32_VMX_PROCBASED_CTLS_MSR);
#ifdef __x86_64__
@@ -92,7 +96,18 @@ void vmx_init_vmcs_config(void)
_vmx_cpu_based_exec_control = adjust_vmx_controls(
min, opt, MSR_IA32_VMX_PROCBASED_CTLS_MSR);
}
+#elif defined(__i386__)
+ if ( !vmx_has_secondary_exec_ctls )
+ _vmx_cpu_based_exec_control &= ~CPU_BASED_TPR_SHADOW;
#endif
+
+ if ( vmx_has_secondary_exec_ctls )
+ {
+ min = 0;
+ opt = SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES;
+ _vmx_secondary_exec_control = adjust_vmx_controls(
+ min, opt, MSR_IA32_VMX_PROCBASED_CTLS2);
+ }
min = VM_EXIT_ACK_INTR_ON_EXIT;
opt = 0;
@@ -113,6 +128,8 @@ void vmx_init_vmcs_config(void)
vmcs_revision_id = vmx_msr_low;
vmx_pin_based_exec_control = _vmx_pin_based_exec_control;
vmx_cpu_based_exec_control = _vmx_cpu_based_exec_control;
+ if ( vmx_has_secondary_exec_ctls )
+ vmx_secondary_exec_control = _vmx_secondary_exec_control;
vmx_vmexit_control = _vmx_vmexit_control;
vmx_vmentry_control = _vmx_vmentry_control;
}
@@ -121,6 +138,8 @@ void vmx_init_vmcs_config(void)
BUG_ON(vmcs_revision_id != vmx_msr_low);
BUG_ON(vmx_pin_based_exec_control != _vmx_pin_based_exec_control);
BUG_ON(vmx_cpu_based_exec_control != _vmx_cpu_based_exec_control);
+ if ( vmx_has_secondary_exec_ctls )
+ BUG_ON(vmx_secondary_exec_control != _vmx_secondary_exec_control);
BUG_ON(vmx_vmexit_control != _vmx_vmexit_control);
BUG_ON(vmx_vmentry_control != _vmx_vmentry_control);
}
@@ -296,6 +315,8 @@ static void construct_vmcs(struct vcpu *
__vmwrite(VM_ENTRY_CONTROLS, vmx_vmentry_control);
__vmwrite(CPU_BASED_VM_EXEC_CONTROL, vmx_cpu_based_exec_control);
v->arch.hvm_vcpu.u.vmx.exec_control = vmx_cpu_based_exec_control;
+ if ( vmx_cpu_based_exec_control & ACTIVATE_SECONDARY_CONTROLS )
+ __vmwrite(SECONDARY_VM_EXEC_CONTROL, vmx_secondary_exec_control);
if ( cpu_has_vmx_msr_bitmap )
__vmwrite(MSR_BITMAP, virt_to_maddr(vmx_msr_bitmap));
@@ -422,7 +443,7 @@ static void construct_vmcs(struct vcpu *
__vmwrite(CR4_READ_SHADOW, v->arch.hvm_vmx.cpu_shadow_cr4);
#ifdef __x86_64__
- /* VLAPIC TPR optimisation. */
+ /* CR8 based VLAPIC TPR optimization. */
if ( cpu_has_vmx_tpr_shadow )
{
__vmwrite(VIRTUAL_APIC_PAGE_ADDR,
@@ -430,6 +451,16 @@ static void construct_vmcs(struct vcpu *
__vmwrite(TPR_THRESHOLD, 0);
}
#endif
+
+ /* Memory-mapped based VLAPIC TPR optimization. */
+ if ( cpu_has_vmx_mmap_vtpr_optimization )
+ {
+ __vmwrite(VIRTUAL_APIC_PAGE_ADDR,
+ page_to_maddr(vcpu_vlapic(v)->regs_page));
+ __vmwrite(TPR_THRESHOLD, 0);
+
+ vcpu_vlapic(v)->mmap_vtpr_enabled = 1;
+ }
__vmwrite(GUEST_LDTR_SELECTOR, 0);
__vmwrite(GUEST_LDTR_BASE, 0);
@@ -499,6 +530,18 @@ void vmx_do_resume(struct vcpu *v)
vmx_load_vmcs(v);
hvm_migrate_timers(v);
vmx_set_host_env(v);
+ }
+
+ if ( !v->arch.hvm_vmx.launched && vcpu_vlapic(v)->mmap_vtpr_enabled )
+ {
+ struct page_info *pg = change_guest_physmap_for_vtpr(v->domain, 1);
+
+ if ( pg == NULL )
+ {
+ gdprintk(XENLOG_ERR, "change_guest_physmap_for_vtpr failed!\n");
+ domain_crash_synchronous();
+ }
+ __vmwrite(APIC_ACCESS_ADDR, page_to_maddr(pg));
}
debug_state = v->domain->debugger_attached;
diff -r 8f147a735faf xen/arch/x86/hvm/vmx/vmx.c
--- a/xen/arch/x86/hvm/vmx/vmx.c Fri Aug 17 14:47:30 2007 -0400
+++ b/xen/arch/x86/hvm/vmx/vmx.c Fri Aug 17 14:47:32 2007 -0400
@@ -2593,6 +2593,114 @@ done:
return 1;
}
+struct page_info * change_guest_physmap_for_vtpr(struct domain *d,
+ int enable_vtpr)
+{
+ struct page_info *pg;
+ unsigned long pfn, mfn;
+
+ spin_lock(&d->arch.hvm_domain.vapic_access_lock);
+
+ pg = d->arch.hvm_domain.apic_access_page;
+ pfn = paddr_to_pfn(APIC_DEFAULT_PHYS_BASE);
+
+ if ( enable_vtpr )
+ {
+ if ( d->arch.hvm_domain.physmap_changed_for_vlapic_access )
+ goto out;
+
+ if ( pg == NULL )
+ pg = alloc_domheap_page(d);
+ if ( pg == NULL )
+ {
+ gdprintk(XENLOG_ERR, "alloc_domheap_pages() failed!\n");
+ goto out;
+ }
+
+ mfn = page_to_mfn(pg);
+ d->arch.hvm_domain.apic_access_page = pg;
+
+ guest_physmap_add_page(d, pfn, mfn);
+
+ d->arch.hvm_domain.physmap_changed_for_vlapic_access = 1;
+
+ goto out;
+ }
+ else
+ {
+ if ( d->arch.hvm_domain.physmap_changed_for_vlapic_access )
+ {
+ mfn = page_to_mfn(pg);
+ guest_physmap_remove_page(d, pfn, mfn);
+ flush_tlb_mask(d->domain_dirty_cpumask);
+
+ d->arch.hvm_domain.physmap_changed_for_vlapic_access = 0;
+ }
+ pg = NULL;
+ goto out;
+ }
+
+out:
+ spin_unlock(&d->arch.hvm_domain.vapic_access_lock);
+ return pg;
+}
+
+static void check_vlapic_msr_for_vtpr(struct vcpu *v)
+{
+ struct vlapic *vlapic = vcpu_vlapic(v);
+ int mmap_vtpr_enabled = vcpu_vlapic(v)->mmap_vtpr_enabled;
+ uint32_t tmp;
+
+
+ if ( vlapic_hw_disabled(vlapic) && mmap_vtpr_enabled )
+ {
+ vcpu_vlapic(v)->mmap_vtpr_enabled = 0;
+
+#ifdef __i386__
+ v->arch.hvm_vcpu.u.vmx.exec_control &= ~CPU_BASED_TPR_SHADOW;
+ __vmwrite(CPU_BASED_VM_EXEC_CONTROL,
+ v->arch.hvm_vcpu.u.vmx.exec_control);
+#elif defined(__x86_64__)
+ if ( !cpu_has_vmx_tpr_shadow )
+ {
+ v->arch.hvm_vcpu.u.vmx.exec_control &= ~CPU_BASED_TPR_SHADOW;
+ __vmwrite(CPU_BASED_VM_EXEC_CONTROL,
+ v->arch.hvm_vcpu.u.vmx.exec_control);
+ }
+#endif
+ tmp = __vmread(SECONDARY_VM_EXEC_CONTROL);
+ tmp &= ~SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES;
+ __vmwrite(SECONDARY_VM_EXEC_CONTROL, tmp);
+
+ change_guest_physmap_for_vtpr(v->domain, 0);
+ }
+ else if ( !vlapic_hw_disabled(vlapic) && !mmap_vtpr_enabled &&
+ cpu_has_vmx_mmap_vtpr_optimization )
+ {
+ vcpu_vlapic(v)->mmap_vtpr_enabled = 1;
+
+ v->arch.hvm_vcpu.u.vmx.exec_control |=
+ ( ACTIVATE_SECONDARY_CONTROLS | CPU_BASED_TPR_SHADOW );
+ __vmwrite(CPU_BASED_VM_EXEC_CONTROL,
+ v->arch.hvm_vcpu.u.vmx.exec_control);
+ tmp = __vmread(SECONDARY_VM_EXEC_CONTROL);
+ tmp |= SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES;
+ __vmwrite(SECONDARY_VM_EXEC_CONTROL, tmp);
+
+ change_guest_physmap_for_vtpr(v->domain, 1);
+ }
+
+ if ( vcpu_vlapic(v)->mmap_vtpr_enabled &&
+ !vlapic_hw_disabled(vlapic) &&
+ (vlapic_base_address(vlapic) != APIC_DEFAULT_PHYS_BASE) )
+ {
+ gdprintk(XENLOG_ERR,
+ "Local APIC base address is set to 0x%016"PRIx64"!\n",
+ vlapic_base_address(vlapic));
+ domain_crash_synchronous();
+ }
+}
+
static inline int vmx_do_msr_write(struct cpu_user_regs *regs)
{
u32 ecx = regs->ecx;
@@ -2621,6 +2729,7 @@ static inline int vmx_do_msr_write(struc
break;
case MSR_IA32_APICBASE:
vlapic_msr_set(vcpu_vlapic(v), msr_content);
+ check_vlapic_msr_for_vtpr(v);
break;
default:
if ( !long_mode_do_msr_write(regs) )
@@ -2955,6 +3064,15 @@ asmlinkage void vmx_vmexit_handler(struc
case EXIT_REASON_TPR_BELOW_THRESHOLD:
break;
+ case EXIT_REASON_APIC_ACCESS:
+ {
+ unsigned long offset;
+
+ exit_qualification = __vmread(EXIT_QUALIFICATION);
+ offset = exit_qualification & 0x0fffUL;
+ handle_mmio(APIC_DEFAULT_PHYS_BASE | offset);
+ break;
+ }
default:
exit_and_crash:
diff -r 8f147a735faf xen/include/asm-x86/hvm/domain.h
--- a/xen/include/asm-x86/hvm/domain.h Fri Aug 17 14:47:30 2007 -0400
+++ b/xen/include/asm-x86/hvm/domain.h Fri Aug 17 14:47:32 2007 -0400
@@ -41,6 +41,11 @@ struct hvm_domain {
s64 tsc_frequency;
struct pl_time pl_time;
+ /* For memory-mapped vLAPIC/vTPR access optimization */
+ spinlock_t vapic_access_lock;
+ int physmap_changed_for_vlapic_access : 1;
+ struct page_info *apic_access_page;
+
struct hvm_io_handler io_handler;
/* Lock protects access to irq, vpic and vioapic. */
diff -r 8f147a735faf xen/include/asm-x86/hvm/vlapic.h
--- a/xen/include/asm-x86/hvm/vlapic.h Fri Aug 17 14:47:30 2007 -0400
+++ b/xen/include/asm-x86/hvm/vlapic.h Fri Aug 17 14:47:32 2007 -0400
@@ -49,12 +49,17 @@
#define vlapic_disabled(vlapic) ((vlapic)->hw.disabled)
#define vlapic_enabled(vlapic) (!vlapic_disabled(vlapic))
+#define vlapic_base_address(vlapic) \
+ (vlapic->hw.apic_base_msr & MSR_IA32_APICBASE_BASE)
+
struct vlapic {
struct hvm_hw_lapic hw;
struct hvm_hw_lapic_regs *regs;
struct periodic_time pt;
s_time_t timer_last_update;
struct page_info *regs_page;
+
+ int mmap_vtpr_enabled : 1;
};
static inline uint32_t vlapic_get_reg(struct vlapic *vlapic, uint32_t reg)
diff -r 8f147a735faf xen/include/asm-x86/hvm/vmx/vmcs.h
--- a/xen/include/asm-x86/hvm/vmx/vmcs.h Fri Aug 17 14:47:30 2007 -0400
+++ b/xen/include/asm-x86/hvm/vmx/vmcs.h Fri Aug 17 14:47:32 2007 -0400
@@ -104,6 +104,7 @@ void vmx_vmcs_exit(struct vcpu *v);
#define CPU_BASED_ACTIVATE_MSR_BITMAP 0x10000000
#define CPU_BASED_MONITOR_EXITING 0x20000000
#define CPU_BASED_PAUSE_EXITING 0x40000000
+#define ACTIVATE_SECONDARY_CONTROLS 0x80000000
extern u32 vmx_cpu_based_exec_control;
#define PIN_BASED_EXT_INTR_MASK 0x00000001
@@ -119,8 +120,16 @@ extern u32 vmx_vmexit_control;
#define VM_ENTRY_DEACT_DUAL_MONITOR 0x00000800
extern u32 vmx_vmentry_control;
+#define SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES 0x00000001
+extern u32 vmx_secondary_exec_control;
+
+#define cpu_has_vmx_virtualize_apic_accesses \
+ (vmx_secondary_exec_control & SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES)
#define cpu_has_vmx_tpr_shadow \
(vmx_cpu_based_exec_control & CPU_BASED_TPR_SHADOW)
+#define cpu_has_vmx_mmap_vtpr_optimization \
+ (cpu_has_vmx_virtualize_apic_accesses && cpu_has_vmx_tpr_shadow)
+
#define cpu_has_vmx_msr_bitmap \
(vmx_cpu_based_exec_control & CPU_BASED_ACTIVATE_MSR_BITMAP)
extern char *vmx_msr_bitmap;
@@ -158,6 +167,8 @@ enum vmcs_field {
TSC_OFFSET_HIGH = 0x00002011,
VIRTUAL_APIC_PAGE_ADDR = 0x00002012,
VIRTUAL_APIC_PAGE_ADDR_HIGH = 0x00002013,
+ APIC_ACCESS_ADDR = 0x00002014,
+ APIC_ACCESS_ADDR_HIGH = 0x00002015,
VMCS_LINK_POINTER = 0x00002800,
VMCS_LINK_POINTER_HIGH = 0x00002801,
GUEST_IA32_DEBUGCTL = 0x00002802,
diff -r 8f147a735faf xen/include/asm-x86/hvm/vmx/vmx.h
--- a/xen/include/asm-x86/hvm/vmx/vmx.h Fri Aug 17 14:47:30 2007 -0400
+++ b/xen/include/asm-x86/hvm/vmx/vmx.h Fri Aug 17 14:47:32 2007 -0400
@@ -32,6 +32,9 @@ void vmx_intr_assist(void);
void vmx_intr_assist(void);
void vmx_do_resume(struct vcpu *);
void set_guest_time(struct vcpu *v, u64 gtime);
+
+extern struct page_info *change_guest_physmap_for_vtpr(struct domain *d,
+ int enable_vtpr);
/*
* Exit Reasons
@@ -81,6 +84,7 @@ void set_guest_time(struct vcpu *v, u64
#define EXIT_REASON_MACHINE_CHECK 41
#define EXIT_REASON_TPR_BELOW_THRESHOLD 43
+#define EXIT_REASON_APIC_ACCESS 44
/*
* Interruption-information format
diff -r 8f147a735faf xen/include/asm-x86/msr.h
--- a/xen/include/asm-x86/msr.h Fri Aug 17 14:47:30 2007 -0400
+++ b/xen/include/asm-x86/msr.h Fri Aug 17 14:47:32 2007 -0400
@@ -117,6 +117,7 @@ static inline void wrmsrl(unsigned int m
#define MSR_IA32_VMX_CR0_FIXED1 0x487
#define MSR_IA32_VMX_CR4_FIXED0 0x488
#define MSR_IA32_VMX_CR4_FIXED1 0x489
+#define MSR_IA32_VMX_PROCBASED_CTLS2 0x48b
#define IA32_FEATURE_CONTROL_MSR 0x3a
#define IA32_FEATURE_CONTROL_MSR_LOCK 0x1
#define IA32_FEATURE_CONTROL_MSR_ENABLE_VMXON 0x4
_______________________________________________
Xen-devel mailing list
Xen-devel@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-devel
|