From 9ff787bf61a4124d93107f3ae45881b26f3329a1 Mon Sep 17 00:00:00 2001 From: Subv Date: Wed, 10 Oct 2018 18:59:27 -0500 Subject: [PATCH] Kernel/Memory: Added a function to first a suitable guest address at which to allocate a region of a given size. --- src/core/hle/kernel/vm_manager.cpp | 22 ++++++++++++++++++++++ src/core/hle/kernel/vm_manager.h | 8 ++++++++ 2 files changed, 30 insertions(+) diff --git a/src/core/hle/kernel/vm_manager.cpp b/src/core/hle/kernel/vm_manager.cpp index e412309fdd..f79ada52b6 100644 --- a/src/core/hle/kernel/vm_manager.cpp +++ b/src/core/hle/kernel/vm_manager.cpp @@ -119,6 +119,28 @@ ResultVal VMManager::MapMemoryBlock(VAddr target, return MakeResult(MergeAdjacent(vma_handle)); } +ResultVal VMManager::FindFreeRegion(u32 size) { + VAddr base = GetAddressSpaceBaseAddress(); + + // Find the first Free VMA. + VMAHandle vma_handle = std::find_if(vma_map.begin(), vma_map.end(), [&](const auto& vma) { + if (vma.second.type != VMAType::Free) + return false; + + VAddr vma_end = vma.second.base + vma.second.size; + return vma_end > base && vma_end >= base + size; + }); + + if (vma_handle == vma_map.end()) { + // TODO(Subv): Find the correct error code here. + return ResultCode(-1); + } + + VAddr target = std::max(base, vma_handle->second.base); + + return MakeResult(target); +} + ResultVal VMManager::MapBackingMemory(VAddr target, u8* memory, u64 size, MemoryState state) { ASSERT(memory != nullptr); diff --git a/src/core/hle/kernel/vm_manager.h b/src/core/hle/kernel/vm_manager.h index 015559a64c..096205134d 100644 --- a/src/core/hle/kernel/vm_manager.h +++ b/src/core/hle/kernel/vm_manager.h @@ -147,6 +147,14 @@ public: ResultVal MapMemoryBlock(VAddr target, std::shared_ptr> block, std::size_t offset, u64 size, MemoryState state); + /** + * Finds the first free address that can hold a region of the desired size. + * + * @param size Size of the desired region. + * @returns The found free address. + */ + ResultVal FindFreeRegion(u32 size); + /** * Maps an unmanaged host memory pointer at a given address. *