[PATCH kvm-unit-tests] api: set up EPT identity map

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



This lets us pass the whole 4GB address space down to the "guest".
Recent versions of Linux use addresses above 0xfe000000 for the
stack when running 32-bit programs in 64-bit mode, and this
breaks if we leave the EPT identity map at the default address
(0xfe000000).

Signed-off-by: Paolo Bonzini <pbonzini@xxxxxxxxxx>
---
 api/identity.cc | 18 +++++++-----------
 api/kvmxx.cc    |  5 +++++
 api/kvmxx.hh    |  1 +
 3 files changed, 13 insertions(+), 11 deletions(-)

diff --git a/api/identity.cc b/api/identity.cc
index a178f3a..2e7987f 100644
--- a/api/identity.cc
+++ b/api/identity.cc
@@ -20,7 +20,7 @@ hole::hole(void* address, size_t size)
 
 vm::vm(kvm::vm& vm, mem_map& mmap, hole h)
 {
-    posix_memalign(&tss, 4096, 3 * 4096);
+    posix_memalign(&tss, 4096, 4 * 4096);
     if (!tss) {
         throw errno_exception(errno);
     }
@@ -28,31 +28,27 @@ vm::vm(kvm::vm& vm, mem_map& mmap, hole h)
     uint64_t hole_gpa = reinterpret_cast<uintptr_t>(h.address);
     char* hole_hva = static_cast<char*>(h.address);
     uint64_t tss_addr = reinterpret_cast<uintptr_t>(tss);
-    uint64_t tss_end = tss_addr + 3 * 4096;
+    uint64_t tss_end = tss_addr + 4 * 4096;
     uint64_t hole_end = hole_gpa + h.size;
-    uint64_t top = 0xfe000000UL;
 
-    if (hole_end > top) {
-        puts("unlucky memory map :(");
-        throw std::exception();
-    }
     if (hole_gpa < tss_addr) {
         if (hole_gpa) {
             _slots.push_back(mem_slot_ptr(new mem_slot(mmap, 0, hole_gpa, NULL)));
         }
         _slots.push_back(mem_slot_ptr(new mem_slot(mmap, hole_end, tss_addr - hole_end,
 						   hole_hva + h.size)));
-        _slots.push_back(mem_slot_ptr(new mem_slot(mmap, tss_end, (uint32_t)top - tss_end,
-						   (char*)tss + 3 * 4096)));
+        _slots.push_back(mem_slot_ptr(new mem_slot(mmap, tss_end, (uint32_t)-tss_end,
+						   (char*)tss + 4 * 4096)));
     } else {
         _slots.push_back(mem_slot_ptr(new mem_slot(mmap, 0, tss_addr, NULL)));
         _slots.push_back(mem_slot_ptr(new mem_slot(mmap, tss_end, hole_gpa - tss_end,
-						   (char*)tss + 3 * 4096)));
-        _slots.push_back(mem_slot_ptr(new mem_slot(mmap, hole_end, (uint32_t)top - hole_end,
+						   (char*)tss + 4 * 4096)));
+        _slots.push_back(mem_slot_ptr(new mem_slot(mmap, hole_end, (uint32_t)-hole_end,
 						   hole_hva + h.size)));
     }
 
     vm.set_tss_addr(tss_addr);
+    vm.set_ept_identity_map_addr(tss_addr + 3 * 4096);
 }
 
 vm::~vm()
diff --git a/api/kvmxx.cc b/api/kvmxx.cc
index 1df6f38..313902e 100644
--- a/api/kvmxx.cc
+++ b/api/kvmxx.cc
@@ -176,6 +176,11 @@ void vm::set_tss_addr(uint32_t addr)
     _fd.ioctl(KVM_SET_TSS_ADDR, addr);
 }
 
+void vm::set_ept_identity_map_addr(uint64_t addr)
+{
+    _fd.ioctlp(KVM_SET_IDENTITY_MAP_ADDR, &addr);
+}
+
 system::system(std::string device_node)
     : _fd(device_node, O_RDWR)
 {
diff --git a/api/kvmxx.hh b/api/kvmxx.hh
index 1dcb41d..e39bd5b 100644
--- a/api/kvmxx.hh
+++ b/api/kvmxx.hh
@@ -61,6 +61,7 @@ public:
                            uint32_t flags = 0);
     void get_dirty_log(int slot, void *log);
     void set_tss_addr(uint32_t addr);
+    void set_ept_identity_map_addr(uint64_t addr);
     system& sys() { return _system; }
 private:
     system& _system;
-- 
1.8.3.1




[Index of Archives]     [KVM ARM]     [KVM ia64]     [KVM ppc]     [Virtualization Tools]     [Spice Development]     [Libvirt]     [Libvirt Users]     [Linux USB Devel]     [Linux Audio Users]     [Yosemite Questions]     [Linux Kernel]     [Linux SCSI]     [XFree86]

  Powered by Linux