]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/blob - releases/2.6.32.12/kvm-x86-emulator-add-virtual-8086-mode-of-emulation.patch
Fixes for 4.19
[thirdparty/kernel/stable-queue.git] / releases / 2.6.32.12 / kvm-x86-emulator-add-virtual-8086-mode-of-emulation.patch
1 From stefan.bader@canonical.com Wed Apr 7 14:41:50 2010
2 From: Gleb Natapov <gleb@redhat.com>
3 Date: Fri, 19 Mar 2010 15:47:30 +0100
4 Subject: KVM: x86 emulator: Add Virtual-8086 mode of emulation
5 To: stable@kernel.org
6 Cc: Marcelo Tosatti <mtosatti@redhat.com>, Avi Kivity <avi@redhat.com>, Gleb Natapov <gleb@redhat.com>
7 Message-ID: <1269010059-25309-3-git-send-email-stefan.bader@canonical.com>
8
9
10 From: Gleb Natapov <gleb@redhat.com>
11
12 commit a0044755679f3e761b8b95995e5f2db2b7efd0f6 upstream
13
14 For some instructions CPU behaves differently for real-mode and
15 virtual 8086. Let emulator know which mode cpu is in, so it will
16 not poke into vcpu state directly.
17
18 Signed-off-by: Gleb Natapov <gleb@redhat.com>
19 Signed-off-by: Avi Kivity <avi@redhat.com>
20 Signed-off-by: Stefan Bader <stefan.bader@canonical.com>
21 Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
22 ---
23 arch/x86/include/asm/kvm_emulate.h | 1 +
24 arch/x86/kvm/emulate.c | 14 +++++++-------
25 arch/x86/kvm/x86.c | 3 ++-
26 3 files changed, 10 insertions(+), 8 deletions(-)
27
28 --- a/arch/x86/include/asm/kvm_emulate.h
29 +++ b/arch/x86/include/asm/kvm_emulate.h
30 @@ -168,6 +168,7 @@ struct x86_emulate_ctxt {
31
32 /* Execution mode, passed to the emulator. */
33 #define X86EMUL_MODE_REAL 0 /* Real mode. */
34 +#define X86EMUL_MODE_VM86 1 /* Virtual 8086 mode. */
35 #define X86EMUL_MODE_PROT16 2 /* 16-bit protected mode. */
36 #define X86EMUL_MODE_PROT32 4 /* 32-bit protected mode. */
37 #define X86EMUL_MODE_PROT64 8 /* 64-bit (long) mode. */
38 --- a/arch/x86/kvm/emulate.c
39 +++ b/arch/x86/kvm/emulate.c
40 @@ -895,6 +895,7 @@ x86_decode_insn(struct x86_emulate_ctxt
41
42 switch (mode) {
43 case X86EMUL_MODE_REAL:
44 + case X86EMUL_MODE_VM86:
45 case X86EMUL_MODE_PROT16:
46 def_op_bytes = def_ad_bytes = 2;
47 break;
48 @@ -1453,7 +1454,7 @@ emulate_syscall(struct x86_emulate_ctxt
49
50 /* syscall is not available in real mode */
51 if (c->lock_prefix || ctxt->mode == X86EMUL_MODE_REAL
52 - || !(ctxt->vcpu->arch.cr0 & X86_CR0_PE))
53 + || ctxt->mode == X86EMUL_MODE_VM86)
54 return -1;
55
56 setup_syscalls_segments(ctxt, &cs, &ss);
57 @@ -1505,9 +1506,8 @@ emulate_sysenter(struct x86_emulate_ctxt
58 if (c->lock_prefix)
59 return -1;
60
61 - /* inject #GP if in real mode or paging is disabled */
62 - if (ctxt->mode == X86EMUL_MODE_REAL ||
63 - !(ctxt->vcpu->arch.cr0 & X86_CR0_PE)) {
64 + /* inject #GP if in real mode */
65 + if (ctxt->mode == X86EMUL_MODE_REAL) {
66 kvm_inject_gp(ctxt->vcpu, 0);
67 return -1;
68 }
69 @@ -1571,9 +1571,9 @@ emulate_sysexit(struct x86_emulate_ctxt
70 if (c->lock_prefix)
71 return -1;
72
73 - /* inject #GP if in real mode or paging is disabled */
74 - if (ctxt->mode == X86EMUL_MODE_REAL
75 - || !(ctxt->vcpu->arch.cr0 & X86_CR0_PE)) {
76 + /* inject #GP if in real mode or Virtual 8086 mode */
77 + if (ctxt->mode == X86EMUL_MODE_REAL ||
78 + ctxt->mode == X86EMUL_MODE_VM86) {
79 kvm_inject_gp(ctxt->vcpu, 0);
80 return -1;
81 }
82 --- a/arch/x86/kvm/x86.c
83 +++ b/arch/x86/kvm/x86.c
84 @@ -2828,8 +2828,9 @@ int emulate_instruction(struct kvm_vcpu
85 vcpu->arch.emulate_ctxt.vcpu = vcpu;
86 vcpu->arch.emulate_ctxt.eflags = kvm_x86_ops->get_rflags(vcpu);
87 vcpu->arch.emulate_ctxt.mode =
88 + (!(vcpu->arch.cr0 & X86_CR0_PE)) ? X86EMUL_MODE_REAL :
89 (vcpu->arch.emulate_ctxt.eflags & X86_EFLAGS_VM)
90 - ? X86EMUL_MODE_REAL : cs_l
91 + ? X86EMUL_MODE_VM86 : cs_l
92 ? X86EMUL_MODE_PROT64 : cs_db
93 ? X86EMUL_MODE_PROT32 : X86EMUL_MODE_PROT16;
94