diff options
-rw-r--r-- | drivers/kvm/kvm.h | 9 | ||||
-rw-r--r-- | drivers/kvm/kvm_main.c | 33 | ||||
-rw-r--r-- | drivers/kvm/paging_tmpl.h | 2 |
3 files changed, 25 insertions, 19 deletions
diff --git a/drivers/kvm/kvm.h b/drivers/kvm/kvm.h index 7117c3b3cca..983c33f3837 100644 --- a/drivers/kvm/kvm.h +++ b/drivers/kvm/kvm.h | |||
@@ -19,12 +19,9 @@ | |||
19 | #include <linux/kvm.h> | 19 | #include <linux/kvm.h> |
20 | #include <linux/kvm_para.h> | 20 | #include <linux/kvm_para.h> |
21 | 21 | ||
22 | #define CR3_WPT_MASK (1ULL << 3) | 22 | #define CR3_PAE_RESERVED_BITS ((X86_CR3_PWT | X86_CR3_PCD) - 1) |
23 | #define CR3_PCD_MASK (1ULL << 4) | 23 | #define CR3_NONPAE_RESERVED_BITS ((PAGE_SIZE-1) & ~(X86_CR3_PWT | X86_CR3_PCD)) |
24 | 24 | #define CR3_L_MODE_RESERVED_BITS (CR3_NONPAE_RESERVED_BITS|0xFFFFFF0000000000ULL) | |
25 | #define CR3_RESEVED_BITS 0x07ULL | ||
26 | #define CR3_L_MODE_RESEVED_BITS (~((1ULL << 40) - 1) | 0x0fe7ULL) | ||
27 | #define CR3_FLAGS_MASK ((1ULL << 5) - 1) | ||
28 | 25 | ||
29 | #define CR4_VME_MASK (1ULL << 0) | 26 | #define CR4_VME_MASK (1ULL << 0) |
30 | #define CR4_PSE_MASK (1ULL << 4) | 27 | #define CR4_PSE_MASK (1ULL << 4) |
diff --git a/drivers/kvm/kvm_main.c b/drivers/kvm/kvm_main.c index 5d8febe580d..34a571dee51 100644 --- a/drivers/kvm/kvm_main.c +++ b/drivers/kvm/kvm_main.c | |||
@@ -571,23 +571,32 @@ EXPORT_SYMBOL_GPL(set_cr4); | |||
571 | void set_cr3(struct kvm_vcpu *vcpu, unsigned long cr3) | 571 | void set_cr3(struct kvm_vcpu *vcpu, unsigned long cr3) |
572 | { | 572 | { |
573 | if (is_long_mode(vcpu)) { | 573 | if (is_long_mode(vcpu)) { |
574 | if (cr3 & CR3_L_MODE_RESEVED_BITS) { | 574 | if (cr3 & CR3_L_MODE_RESERVED_BITS) { |
575 | printk(KERN_DEBUG "set_cr3: #GP, reserved bits\n"); | 575 | printk(KERN_DEBUG "set_cr3: #GP, reserved bits\n"); |
576 | inject_gp(vcpu); | 576 | inject_gp(vcpu); |
577 | return; | 577 | return; |
578 | } | 578 | } |
579 | } else { | 579 | } else { |
580 | if (cr3 & CR3_RESEVED_BITS) { | 580 | if (is_pae(vcpu)) { |
581 | printk(KERN_DEBUG "set_cr3: #GP, reserved bits\n"); | 581 | if (cr3 & CR3_PAE_RESERVED_BITS) { |
582 | inject_gp(vcpu); | 582 | printk(KERN_DEBUG |
583 | return; | 583 | "set_cr3: #GP, reserved bits\n"); |
584 | } | 584 | inject_gp(vcpu); |
585 | if (is_paging(vcpu) && is_pae(vcpu) && | 585 | return; |
586 | !load_pdptrs(vcpu, cr3)) { | 586 | } |
587 | printk(KERN_DEBUG "set_cr3: #GP, pdptrs " | 587 | if (is_paging(vcpu) && !load_pdptrs(vcpu, cr3)) { |
588 | "reserved bits\n"); | 588 | printk(KERN_DEBUG "set_cr3: #GP, pdptrs " |
589 | inject_gp(vcpu); | 589 | "reserved bits\n"); |
590 | return; | 590 | inject_gp(vcpu); |
591 | return; | ||
592 | } | ||
593 | } else { | ||
594 | if (cr3 & CR3_NONPAE_RESERVED_BITS) { | ||
595 | printk(KERN_DEBUG | ||
596 | "set_cr3: #GP, reserved bits\n"); | ||
597 | inject_gp(vcpu); | ||
598 | return; | ||
599 | } | ||
591 | } | 600 | } |
592 | } | 601 | } |
593 | 602 | ||
diff --git a/drivers/kvm/paging_tmpl.h b/drivers/kvm/paging_tmpl.h index 4b5391c717f..01901ec3fe8 100644 --- a/drivers/kvm/paging_tmpl.h +++ b/drivers/kvm/paging_tmpl.h | |||
@@ -99,7 +99,7 @@ static int FNAME(walk_addr)(struct guest_walker *walker, | |||
99 | walker->table = kmap_atomic(pfn_to_page(hpa >> PAGE_SHIFT), KM_USER0); | 99 | walker->table = kmap_atomic(pfn_to_page(hpa >> PAGE_SHIFT), KM_USER0); |
100 | 100 | ||
101 | ASSERT((!is_long_mode(vcpu) && is_pae(vcpu)) || | 101 | ASSERT((!is_long_mode(vcpu) && is_pae(vcpu)) || |
102 | (vcpu->cr3 & ~(PAGE_MASK | CR3_FLAGS_MASK)) == 0); | 102 | (vcpu->cr3 & CR3_NONPAE_RESERVED_BITS) == 0); |
103 | 103 | ||
104 | walker->inherited_ar = PT_USER_MASK | PT_WRITABLE_MASK; | 104 | walker->inherited_ar = PT_USER_MASK | PT_WRITABLE_MASK; |
105 | 105 | ||