diff options
| author | 2021-05-07 23:30:17 -0700 | |
|---|---|---|
| committer | 2021-05-07 23:30:17 -0700 | |
| commit | faa067f175cbf5e916ed75776817f0046e6731c4 (patch) | |
| tree | 8ab02a72a6e4d6578848c8da2c02af02684aeec7 /src/core/memory.cpp | |
| parent | Merge pull request #6287 from lioncash/ldr-copy (diff) | |
| parent | hle: kernel: KPageTable: CanContain should not be constexpr. (diff) | |
| download | yuzu-faa067f175cbf5e916ed75776817f0046e6731c4.tar.gz yuzu-faa067f175cbf5e916ed75776817f0046e6731c4.tar.xz yuzu-faa067f175cbf5e916ed75776817f0046e6731c4.zip | |
Merge pull request #6266 from bunnei/kautoobject-refactor
Kernel Rework: Migrate kernel objects to KAutoObject
Diffstat (limited to 'src/core/memory.cpp')
| -rw-r--r-- | src/core/memory.cpp | 64 |
1 files changed, 46 insertions, 18 deletions
diff --git a/src/core/memory.cpp b/src/core/memory.cpp index b9dd3e275..b4c56e1c1 100644 --- a/src/core/memory.cpp +++ b/src/core/memory.cpp | |||
| @@ -17,8 +17,8 @@ | |||
| 17 | #include "core/core.h" | 17 | #include "core/core.h" |
| 18 | #include "core/device_memory.h" | 18 | #include "core/device_memory.h" |
| 19 | #include "core/hle/kernel/k_page_table.h" | 19 | #include "core/hle/kernel/k_page_table.h" |
| 20 | #include "core/hle/kernel/k_process.h" | ||
| 20 | #include "core/hle/kernel/physical_memory.h" | 21 | #include "core/hle/kernel/physical_memory.h" |
| 21 | #include "core/hle/kernel/process.h" | ||
| 22 | #include "core/memory.h" | 22 | #include "core/memory.h" |
| 23 | #include "video_core/gpu.h" | 23 | #include "video_core/gpu.h" |
| 24 | 24 | ||
| @@ -30,7 +30,7 @@ namespace Core::Memory { | |||
| 30 | struct Memory::Impl { | 30 | struct Memory::Impl { |
| 31 | explicit Impl(Core::System& system_) : system{system_} {} | 31 | explicit Impl(Core::System& system_) : system{system_} {} |
| 32 | 32 | ||
| 33 | void SetCurrentPageTable(Kernel::Process& process, u32 core_id) { | 33 | void SetCurrentPageTable(Kernel::KProcess& process, u32 core_id) { |
| 34 | current_page_table = &process.PageTable().PageTableImpl(); | 34 | current_page_table = &process.PageTable().PageTableImpl(); |
| 35 | 35 | ||
| 36 | const std::size_t address_space_width = process.PageTable().GetAddressSpaceWidth(); | 36 | const std::size_t address_space_width = process.PageTable().GetAddressSpaceWidth(); |
| @@ -50,7 +50,7 @@ struct Memory::Impl { | |||
| 50 | MapPages(page_table, base / PAGE_SIZE, size / PAGE_SIZE, 0, Common::PageType::Unmapped); | 50 | MapPages(page_table, base / PAGE_SIZE, size / PAGE_SIZE, 0, Common::PageType::Unmapped); |
| 51 | } | 51 | } |
| 52 | 52 | ||
| 53 | bool IsValidVirtualAddress(const Kernel::Process& process, const VAddr vaddr) const { | 53 | bool IsValidVirtualAddress(const Kernel::KProcess& process, const VAddr vaddr) const { |
| 54 | const auto& page_table = process.PageTable().PageTableImpl(); | 54 | const auto& page_table = process.PageTable().PageTableImpl(); |
| 55 | const auto [pointer, type] = page_table.pointers[vaddr >> PAGE_BITS].PointerType(); | 55 | const auto [pointer, type] = page_table.pointers[vaddr >> PAGE_BITS].PointerType(); |
| 56 | return pointer != nullptr || type == Common::PageType::RasterizerCachedMemory; | 56 | return pointer != nullptr || type == Common::PageType::RasterizerCachedMemory; |
| @@ -82,6 +82,22 @@ struct Memory::Impl { | |||
| 82 | return nullptr; | 82 | return nullptr; |
| 83 | } | 83 | } |
| 84 | 84 | ||
| 85 | u8* GetKernelBuffer(VAddr start_vaddr, size_t size) { | ||
| 86 | // TODO(bunnei): This is just a workaround until we have kernel memory layout mapped & | ||
| 87 | // managed. Until then, we use this to allocate and access kernel memory regions. | ||
| 88 | |||
| 89 | auto search = kernel_memory_regions.find(start_vaddr); | ||
| 90 | if (search != kernel_memory_regions.end()) { | ||
| 91 | return search->second.get(); | ||
| 92 | } | ||
| 93 | |||
| 94 | std::unique_ptr<u8[]> new_memory_region{new u8[size]}; | ||
| 95 | u8* raw_ptr = new_memory_region.get(); | ||
| 96 | kernel_memory_regions[start_vaddr] = std::move(new_memory_region); | ||
| 97 | |||
| 98 | return raw_ptr; | ||
| 99 | } | ||
| 100 | |||
| 85 | u8 Read8(const VAddr addr) { | 101 | u8 Read8(const VAddr addr) { |
| 86 | return Read<u8>(addr); | 102 | return Read<u8>(addr); |
| 87 | } | 103 | } |
| @@ -178,7 +194,7 @@ struct Memory::Impl { | |||
| 178 | return string; | 194 | return string; |
| 179 | } | 195 | } |
| 180 | 196 | ||
| 181 | void ReadBlock(const Kernel::Process& process, const VAddr src_addr, void* dest_buffer, | 197 | void ReadBlock(const Kernel::KProcess& process, const VAddr src_addr, void* dest_buffer, |
| 182 | const std::size_t size) { | 198 | const std::size_t size) { |
| 183 | const auto& page_table = process.PageTable().PageTableImpl(); | 199 | const auto& page_table = process.PageTable().PageTableImpl(); |
| 184 | 200 | ||
| @@ -223,7 +239,7 @@ struct Memory::Impl { | |||
| 223 | } | 239 | } |
| 224 | } | 240 | } |
| 225 | 241 | ||
| 226 | void ReadBlockUnsafe(const Kernel::Process& process, const VAddr src_addr, void* dest_buffer, | 242 | void ReadBlockUnsafe(const Kernel::KProcess& process, const VAddr src_addr, void* dest_buffer, |
| 227 | const std::size_t size) { | 243 | const std::size_t size) { |
| 228 | const auto& page_table = process.PageTable().PageTableImpl(); | 244 | const auto& page_table = process.PageTable().PageTableImpl(); |
| 229 | 245 | ||
| @@ -275,7 +291,7 @@ struct Memory::Impl { | |||
| 275 | ReadBlockUnsafe(*system.CurrentProcess(), src_addr, dest_buffer, size); | 291 | ReadBlockUnsafe(*system.CurrentProcess(), src_addr, dest_buffer, size); |
| 276 | } | 292 | } |
| 277 | 293 | ||
| 278 | void WriteBlock(const Kernel::Process& process, const VAddr dest_addr, const void* src_buffer, | 294 | void WriteBlock(const Kernel::KProcess& process, const VAddr dest_addr, const void* src_buffer, |
| 279 | const std::size_t size) { | 295 | const std::size_t size) { |
| 280 | const auto& page_table = process.PageTable().PageTableImpl(); | 296 | const auto& page_table = process.PageTable().PageTableImpl(); |
| 281 | std::size_t remaining_size = size; | 297 | std::size_t remaining_size = size; |
| @@ -318,7 +334,7 @@ struct Memory::Impl { | |||
| 318 | } | 334 | } |
| 319 | } | 335 | } |
| 320 | 336 | ||
| 321 | void WriteBlockUnsafe(const Kernel::Process& process, const VAddr dest_addr, | 337 | void WriteBlockUnsafe(const Kernel::KProcess& process, const VAddr dest_addr, |
| 322 | const void* src_buffer, const std::size_t size) { | 338 | const void* src_buffer, const std::size_t size) { |
| 323 | const auto& page_table = process.PageTable().PageTableImpl(); | 339 | const auto& page_table = process.PageTable().PageTableImpl(); |
| 324 | std::size_t remaining_size = size; | 340 | std::size_t remaining_size = size; |
| @@ -368,7 +384,7 @@ struct Memory::Impl { | |||
| 368 | WriteBlockUnsafe(*system.CurrentProcess(), dest_addr, src_buffer, size); | 384 | WriteBlockUnsafe(*system.CurrentProcess(), dest_addr, src_buffer, size); |
| 369 | } | 385 | } |
| 370 | 386 | ||
| 371 | void ZeroBlock(const Kernel::Process& process, const VAddr dest_addr, const std::size_t size) { | 387 | void ZeroBlock(const Kernel::KProcess& process, const VAddr dest_addr, const std::size_t size) { |
| 372 | const auto& page_table = process.PageTable().PageTableImpl(); | 388 | const auto& page_table = process.PageTable().PageTableImpl(); |
| 373 | std::size_t remaining_size = size; | 389 | std::size_t remaining_size = size; |
| 374 | std::size_t page_index = dest_addr >> PAGE_BITS; | 390 | std::size_t page_index = dest_addr >> PAGE_BITS; |
| @@ -413,7 +429,7 @@ struct Memory::Impl { | |||
| 413 | ZeroBlock(*system.CurrentProcess(), dest_addr, size); | 429 | ZeroBlock(*system.CurrentProcess(), dest_addr, size); |
| 414 | } | 430 | } |
| 415 | 431 | ||
| 416 | void CopyBlock(const Kernel::Process& process, VAddr dest_addr, VAddr src_addr, | 432 | void CopyBlock(const Kernel::KProcess& process, VAddr dest_addr, VAddr src_addr, |
| 417 | const std::size_t size) { | 433 | const std::size_t size) { |
| 418 | const auto& page_table = process.PageTable().PageTableImpl(); | 434 | const auto& page_table = process.PageTable().PageTableImpl(); |
| 419 | std::size_t remaining_size = size; | 435 | std::size_t remaining_size = size; |
| @@ -711,13 +727,21 @@ struct Memory::Impl { | |||
| 711 | } | 727 | } |
| 712 | 728 | ||
| 713 | Common::PageTable* current_page_table = nullptr; | 729 | Common::PageTable* current_page_table = nullptr; |
| 730 | std::unordered_map<VAddr, std::unique_ptr<u8[]>> kernel_memory_regions; | ||
| 714 | Core::System& system; | 731 | Core::System& system; |
| 715 | }; | 732 | }; |
| 716 | 733 | ||
| 717 | Memory::Memory(Core::System& system) : impl{std::make_unique<Impl>(system)} {} | 734 | Memory::Memory(Core::System& system_) : system{system_} { |
| 735 | Reset(); | ||
| 736 | } | ||
| 737 | |||
| 718 | Memory::~Memory() = default; | 738 | Memory::~Memory() = default; |
| 719 | 739 | ||
| 720 | void Memory::SetCurrentPageTable(Kernel::Process& process, u32 core_id) { | 740 | void Memory::Reset() { |
| 741 | impl = std::make_unique<Impl>(system); | ||
| 742 | } | ||
| 743 | |||
| 744 | void Memory::SetCurrentPageTable(Kernel::KProcess& process, u32 core_id) { | ||
| 721 | impl->SetCurrentPageTable(process, core_id); | 745 | impl->SetCurrentPageTable(process, core_id); |
| 722 | } | 746 | } |
| 723 | 747 | ||
| @@ -729,7 +753,7 @@ void Memory::UnmapRegion(Common::PageTable& page_table, VAddr base, u64 size) { | |||
| 729 | impl->UnmapRegion(page_table, base, size); | 753 | impl->UnmapRegion(page_table, base, size); |
| 730 | } | 754 | } |
| 731 | 755 | ||
| 732 | bool Memory::IsValidVirtualAddress(const Kernel::Process& process, const VAddr vaddr) const { | 756 | bool Memory::IsValidVirtualAddress(const Kernel::KProcess& process, const VAddr vaddr) const { |
| 733 | return impl->IsValidVirtualAddress(process, vaddr); | 757 | return impl->IsValidVirtualAddress(process, vaddr); |
| 734 | } | 758 | } |
| 735 | 759 | ||
| @@ -741,6 +765,10 @@ u8* Memory::GetPointer(VAddr vaddr) { | |||
| 741 | return impl->GetPointer(vaddr); | 765 | return impl->GetPointer(vaddr); |
| 742 | } | 766 | } |
| 743 | 767 | ||
| 768 | u8* Memory::GetKernelBuffer(VAddr start_vaddr, size_t size) { | ||
| 769 | return impl->GetKernelBuffer(start_vaddr, size); | ||
| 770 | } | ||
| 771 | |||
| 744 | const u8* Memory::GetPointer(VAddr vaddr) const { | 772 | const u8* Memory::GetPointer(VAddr vaddr) const { |
| 745 | return impl->GetPointer(vaddr); | 773 | return impl->GetPointer(vaddr); |
| 746 | } | 774 | } |
| @@ -801,7 +829,7 @@ std::string Memory::ReadCString(VAddr vaddr, std::size_t max_length) { | |||
| 801 | return impl->ReadCString(vaddr, max_length); | 829 | return impl->ReadCString(vaddr, max_length); |
| 802 | } | 830 | } |
| 803 | 831 | ||
| 804 | void Memory::ReadBlock(const Kernel::Process& process, const VAddr src_addr, void* dest_buffer, | 832 | void Memory::ReadBlock(const Kernel::KProcess& process, const VAddr src_addr, void* dest_buffer, |
| 805 | const std::size_t size) { | 833 | const std::size_t size) { |
| 806 | impl->ReadBlock(process, src_addr, dest_buffer, size); | 834 | impl->ReadBlock(process, src_addr, dest_buffer, size); |
| 807 | } | 835 | } |
| @@ -810,7 +838,7 @@ void Memory::ReadBlock(const VAddr src_addr, void* dest_buffer, const std::size_ | |||
| 810 | impl->ReadBlock(src_addr, dest_buffer, size); | 838 | impl->ReadBlock(src_addr, dest_buffer, size); |
| 811 | } | 839 | } |
| 812 | 840 | ||
| 813 | void Memory::ReadBlockUnsafe(const Kernel::Process& process, const VAddr src_addr, | 841 | void Memory::ReadBlockUnsafe(const Kernel::KProcess& process, const VAddr src_addr, |
| 814 | void* dest_buffer, const std::size_t size) { | 842 | void* dest_buffer, const std::size_t size) { |
| 815 | impl->ReadBlockUnsafe(process, src_addr, dest_buffer, size); | 843 | impl->ReadBlockUnsafe(process, src_addr, dest_buffer, size); |
| 816 | } | 844 | } |
| @@ -819,7 +847,7 @@ void Memory::ReadBlockUnsafe(const VAddr src_addr, void* dest_buffer, const std: | |||
| 819 | impl->ReadBlockUnsafe(src_addr, dest_buffer, size); | 847 | impl->ReadBlockUnsafe(src_addr, dest_buffer, size); |
| 820 | } | 848 | } |
| 821 | 849 | ||
| 822 | void Memory::WriteBlock(const Kernel::Process& process, VAddr dest_addr, const void* src_buffer, | 850 | void Memory::WriteBlock(const Kernel::KProcess& process, VAddr dest_addr, const void* src_buffer, |
| 823 | std::size_t size) { | 851 | std::size_t size) { |
| 824 | impl->WriteBlock(process, dest_addr, src_buffer, size); | 852 | impl->WriteBlock(process, dest_addr, src_buffer, size); |
| 825 | } | 853 | } |
| @@ -828,7 +856,7 @@ void Memory::WriteBlock(const VAddr dest_addr, const void* src_buffer, const std | |||
| 828 | impl->WriteBlock(dest_addr, src_buffer, size); | 856 | impl->WriteBlock(dest_addr, src_buffer, size); |
| 829 | } | 857 | } |
| 830 | 858 | ||
| 831 | void Memory::WriteBlockUnsafe(const Kernel::Process& process, VAddr dest_addr, | 859 | void Memory::WriteBlockUnsafe(const Kernel::KProcess& process, VAddr dest_addr, |
| 832 | const void* src_buffer, std::size_t size) { | 860 | const void* src_buffer, std::size_t size) { |
| 833 | impl->WriteBlockUnsafe(process, dest_addr, src_buffer, size); | 861 | impl->WriteBlockUnsafe(process, dest_addr, src_buffer, size); |
| 834 | } | 862 | } |
| @@ -838,7 +866,7 @@ void Memory::WriteBlockUnsafe(const VAddr dest_addr, const void* src_buffer, | |||
| 838 | impl->WriteBlockUnsafe(dest_addr, src_buffer, size); | 866 | impl->WriteBlockUnsafe(dest_addr, src_buffer, size); |
| 839 | } | 867 | } |
| 840 | 868 | ||
| 841 | void Memory::ZeroBlock(const Kernel::Process& process, VAddr dest_addr, std::size_t size) { | 869 | void Memory::ZeroBlock(const Kernel::KProcess& process, VAddr dest_addr, std::size_t size) { |
| 842 | impl->ZeroBlock(process, dest_addr, size); | 870 | impl->ZeroBlock(process, dest_addr, size); |
| 843 | } | 871 | } |
| 844 | 872 | ||
| @@ -846,7 +874,7 @@ void Memory::ZeroBlock(VAddr dest_addr, std::size_t size) { | |||
| 846 | impl->ZeroBlock(dest_addr, size); | 874 | impl->ZeroBlock(dest_addr, size); |
| 847 | } | 875 | } |
| 848 | 876 | ||
| 849 | void Memory::CopyBlock(const Kernel::Process& process, VAddr dest_addr, VAddr src_addr, | 877 | void Memory::CopyBlock(const Kernel::KProcess& process, VAddr dest_addr, VAddr src_addr, |
| 850 | const std::size_t size) { | 878 | const std::size_t size) { |
| 851 | impl->CopyBlock(process, dest_addr, src_addr, size); | 879 | impl->CopyBlock(process, dest_addr, src_addr, size); |
| 852 | } | 880 | } |