summaryrefslogtreecommitdiffstats
path: root/src/core/hle/kernel/process.cpp
diff options
context:
space:
mode:
authorbunnei <bunneidev@gmail.com>2017-12-29 03:35:49 +0100
committerbunnei <bunneidev@gmail.com>2017-12-29 03:35:49 +0100
commit3421e1617e0b64ca0b1be18d4fefe769d35244d0 (patch)
tree9999fc9c439a7dd066ba5f062af097906a088aad /src/core/hle/kernel/process.cpp
parentsvc: Implement SetHeapSize. (diff)
downloadyuzu-3421e1617e0b64ca0b1be18d4fefe769d35244d0.tar
yuzu-3421e1617e0b64ca0b1be18d4fefe769d35244d0.tar.gz
yuzu-3421e1617e0b64ca0b1be18d4fefe769d35244d0.tar.bz2
yuzu-3421e1617e0b64ca0b1be18d4fefe769d35244d0.tar.lz
yuzu-3421e1617e0b64ca0b1be18d4fefe769d35244d0.tar.xz
yuzu-3421e1617e0b64ca0b1be18d4fefe769d35244d0.tar.zst
yuzu-3421e1617e0b64ca0b1be18d4fefe769d35244d0.zip
Diffstat (limited to '')
-rw-r--r--src/core/hle/kernel/process.cpp25
1 files changed, 25 insertions, 0 deletions
diff --git a/src/core/hle/kernel/process.cpp b/src/core/hle/kernel/process.cpp
index 98c5b0905..9bcb08fc9 100644
--- a/src/core/hle/kernel/process.cpp
+++ b/src/core/hle/kernel/process.cpp
@@ -267,6 +267,31 @@ ResultCode Process::LinearFree(VAddr target, u32 size) {
return RESULT_SUCCESS;
}
+ResultCode Process::MirrorMemory(VAddr dst_addr, VAddr src_addr, u64 size) {
+ auto vma = vm_manager.FindVMA(src_addr);
+
+ ASSERT_MSG(vma != vm_manager.vma_map.end(), "Invalid memory address");
+ ASSERT_MSG(vma->second.backing_block, "Backing block doesn't exist for address");
+
+ // The returned VMA might be a bigger one encompassing the desired address.
+ auto vma_offset = src_addr - vma->first;
+ ASSERT_MSG(vma_offset + size <= vma->second.size,
+ "Shared memory exceeds bounds of mapped block");
+
+ const std::shared_ptr<std::vector<u8>>& backing_block = vma->second.backing_block;
+ size_t backing_block_offset = vma->second.offset + vma_offset;
+
+ CASCADE_RESULT(auto new_vma,
+ vm_manager.MapMemoryBlock(dst_addr, backing_block, backing_block_offset, size,
+ vma->second.meminfo_state));
+ // Protect mirror with permissions from old region
+ vm_manager.Reprotect(new_vma, vma->second.permissions);
+ // Remove permissions from old region
+ vm_manager.Reprotect(vma, VMAPermission::None);
+
+ return RESULT_SUCCESS;
+}
+
Kernel::Process::Process() {}
Kernel::Process::~Process() {}