Commit f4bbd9aa authored by Avi Kivity's avatar Avi Kivity

KVM: Load real mode segments correctly

Real mode segments to not reference the GDT or LDT; they simply compute
base = selector * 16.
Signed-off-by: default avatarAvi Kivity <avi@qumranet.com>
parent a16b20da
...@@ -3588,11 +3588,33 @@ static int load_segment_descriptor_to_kvm_desct(struct kvm_vcpu *vcpu, ...@@ -3588,11 +3588,33 @@ static int load_segment_descriptor_to_kvm_desct(struct kvm_vcpu *vcpu,
return 0; return 0;
} }
int kvm_load_realmode_segment(struct kvm_vcpu *vcpu, u16 selector, int seg)
{
struct kvm_segment segvar = {
.base = selector << 4,
.limit = 0xffff,
.selector = selector,
.type = 3,
.present = 1,
.dpl = 3,
.db = 0,
.s = 1,
.l = 0,
.g = 0,
.avl = 0,
.unusable = 0,
};
kvm_x86_ops->set_segment(vcpu, &segvar, seg);
return 0;
}
int kvm_load_segment_descriptor(struct kvm_vcpu *vcpu, u16 selector, int kvm_load_segment_descriptor(struct kvm_vcpu *vcpu, u16 selector,
int type_bits, int seg) int type_bits, int seg)
{ {
struct kvm_segment kvm_seg; struct kvm_segment kvm_seg;
if (!(vcpu->arch.cr0 & X86_CR0_PE))
return kvm_load_realmode_segment(vcpu, selector, seg);
if (load_segment_descriptor_to_kvm_desct(vcpu, selector, &kvm_seg)) if (load_segment_descriptor_to_kvm_desct(vcpu, selector, &kvm_seg))
return 1; return 1;
kvm_seg.type |= type_bits; kvm_seg.type |= type_bits;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment