summaryrefslogtreecommitdiff
path: root/src/core/memory.cpp
diff options
context:
space:
mode:
authorGravatar Liam2023-07-25 09:51:06 -0400
committerGravatar Liam2023-07-25 09:51:06 -0400
commit07f71e2620f4a26f251d1708859ba53ffc831c14 (patch)
tree91244a2268d18b9092a6f64112069836eece7583 /src/core/memory.cpp
parentMerge pull request #11095 from liamwhite/memory2 (diff)
downloadyuzu-07f71e2620f4a26f251d1708859ba53ffc831c14.tar.gz
yuzu-07f71e2620f4a26f251d1708859ba53ffc831c14.tar.xz
yuzu-07f71e2620f4a26f251d1708859ba53ffc831c14.zip
memory: check page against address space size
Diffstat (limited to 'src/core/memory.cpp')
-rw-r--r--src/core/memory.cpp21
1 files changed, 18 insertions, 3 deletions
diff --git a/src/core/memory.cpp b/src/core/memory.cpp
index 179685b72..09c53ea92 100644
--- a/src/core/memory.cpp
+++ b/src/core/memory.cpp
@@ -24,6 +24,16 @@
24 24
25namespace Core::Memory { 25namespace Core::Memory {
26 26
27namespace {
28
29bool AddressSpaceContains(const Common::PageTable& table, const Common::ProcessAddress addr,
30 const std::size_t size) {
31 const Common::ProcessAddress max_addr = 1ULL << table.GetAddressSpaceBits();
32 return addr + size >= addr && addr + size <= max_addr;
33}
34
35} // namespace
36
27// Implementation class used to keep the specifics of the memory subsystem hidden 37// Implementation class used to keep the specifics of the memory subsystem hidden
28// from outside classes. This also allows modification to the internals of the memory 38// from outside classes. This also allows modification to the internals of the memory
29// subsystem without needing to rebuild all files that make use of the memory interface. 39// subsystem without needing to rebuild all files that make use of the memory interface.
@@ -191,6 +201,11 @@ struct Memory::Impl {
191 std::size_t page_offset = addr & YUZU_PAGEMASK; 201 std::size_t page_offset = addr & YUZU_PAGEMASK;
192 bool user_accessible = true; 202 bool user_accessible = true;
193 203
204 if (!AddressSpaceContains(page_table, addr, size)) [[unlikely]] {
205 on_unmapped(size, addr);
206 return false;
207 }
208
194 while (remaining_size) { 209 while (remaining_size) {
195 const std::size_t copy_amount = 210 const std::size_t copy_amount =
196 std::min(static_cast<std::size_t>(YUZU_PAGESIZE) - page_offset, remaining_size); 211 std::min(static_cast<std::size_t>(YUZU_PAGESIZE) - page_offset, remaining_size);
@@ -420,7 +435,7 @@ struct Memory::Impl {
420 } 435 }
421 436
422 void MarkRegionDebug(u64 vaddr, u64 size, bool debug) { 437 void MarkRegionDebug(u64 vaddr, u64 size, bool debug) {
423 if (vaddr == 0) { 438 if (vaddr == 0 || !AddressSpaceContains(*current_page_table, vaddr, size)) {
424 return; 439 return;
425 } 440 }
426 441
@@ -476,7 +491,7 @@ struct Memory::Impl {
476 } 491 }
477 492
478 void RasterizerMarkRegionCached(u64 vaddr, u64 size, bool cached) { 493 void RasterizerMarkRegionCached(u64 vaddr, u64 size, bool cached) {
479 if (vaddr == 0) { 494 if (vaddr == 0 || !AddressSpaceContains(*current_page_table, vaddr, size)) {
480 return; 495 return;
481 } 496 }
482 497
@@ -611,7 +626,7 @@ struct Memory::Impl {
611 // AARCH64 masks the upper 16 bit of all memory accesses 626 // AARCH64 masks the upper 16 bit of all memory accesses
612 vaddr = vaddr & 0xffffffffffffULL; 627 vaddr = vaddr & 0xffffffffffffULL;
613 628
614 if (vaddr >= 1uLL << current_page_table->GetAddressSpaceBits()) { 629 if (!AddressSpaceContains(*current_page_table, vaddr, 1)) [[unlikely]] {
615 on_unmapped(); 630 on_unmapped();
616 return nullptr; 631 return nullptr;
617 } 632 }