@@ -991,6 +991,8 @@ void kvm_gsi_routing_write(struct kvm_vm *vm, struct kvm_irq_routing *routing);
const char *exit_reason_str(unsigned int exit_reason);
gpa_t vm_phy_page_alloc(struct kvm_vm *vm, gpa_t min_gpa, u32 memslot);
+gpa_t ____vm_phy_pages_alloc(struct kvm_vm *vm, size_t nr_pages, gpa_t min_gpa,
+ u32 memslot, bool protected, bool naturally_aligned);
gpa_t __vm_phy_pages_alloc(struct kvm_vm *vm, size_t nr_pages, gpa_t min_gpa,
u32 memslot, bool protected);
gpa_t vm_alloc_page_table(struct kvm_vm *vm);
@@ -17,6 +17,7 @@
#include <sys/stat.h>
#include <time.h>
#include <unistd.h>
+#include <linux/align.h>
#include <linux/kernel.h>
#define KVM_UTIL_MIN_PFN 2
@@ -2032,9 +2033,10 @@ const char *exit_reason_str(unsigned int exit_reason)
*
* Note, success is guaranteed!
*/
-gpa_t __vm_phy_pages_alloc(struct kvm_vm *vm, size_t nr_pages, gpa_t min_gpa,
- u32 memslot, bool protected)
+gpa_t ____vm_phy_pages_alloc(struct kvm_vm *vm, size_t nr_pages, gpa_t min_gpa,
+ u32 memslot, bool protected, bool naturally_aligned)
{
+ size_t alignment = naturally_aligned ? nr_pages : 1;
struct userspace_mem_region *region;
sparsebit_idx_t pg, base;
@@ -2051,6 +2053,7 @@ gpa_t __vm_phy_pages_alloc(struct kvm_vm *vm, size_t nr_pages, gpa_t min_gpa,
base = min_gpa >> vm->page_shift;
again:
+ base = ALIGN(base, alignment);
for (pg = base; pg < base + nr_pages; ++pg) {
if (!sparsebit_is_set(region->unused_phy_pages, pg)) {
base = sparsebit_next_set(region->unused_phy_pages, pg);
@@ -2077,6 +2080,12 @@ gpa_t __vm_phy_pages_alloc(struct kvm_vm *vm, size_t nr_pages, gpa_t min_gpa,
__builtin_unreachable();
}
+gpa_t __vm_phy_pages_alloc(struct kvm_vm *vm, size_t nr_pages, gpa_t min_gpa,
+ u32 memslot, bool protected)
+{
+ return ____vm_phy_pages_alloc(vm, nr_pages, min_gpa, memslot, protected, false);
+}
+
gpa_t vm_phy_page_alloc(struct kvm_vm *vm, gpa_t min_gpa, u32 memslot)
{
return vm_phy_pages_alloc(vm, 1, min_gpa, memslot);