diff options
| author | 2021-02-13 00:42:30 -0800 | |
|---|---|---|
| committer | 2021-03-21 14:45:02 -0700 | |
| commit | 778e0f8ec1c1be555217be91a32ac01d32675e23 (patch) | |
| tree | 668c3c7b4c31477a45e2e1f9ad550a1af00901ef /src | |
| parent | Merge pull request #6052 from Morph1984/vi-getindirectlayerimagemap (diff) | |
| download | yuzu-778e0f8ec1c1be555217be91a32ac01d32675e23.tar.gz yuzu-778e0f8ec1c1be555217be91a32ac01d32675e23.tar.xz yuzu-778e0f8ec1c1be555217be91a32ac01d32675e23.zip | |
hle: kernel: Move KMemoryRegion to its own module and update.
Diffstat (limited to 'src')
| -rw-r--r-- | src/core/CMakeLists.txt | 1 | ||||
| -rw-r--r-- | src/core/hle/kernel/k_memory_layout.h | 22 | ||||
| -rw-r--r-- | src/core/hle/kernel/k_memory_region.h | 310 | ||||
| -rw-r--r-- | src/core/hle/kernel/kernel.cpp | 20 |
4 files changed, 322 insertions, 31 deletions
diff --git a/src/core/CMakeLists.txt b/src/core/CMakeLists.txt index 17f251c37..d9eea00ca 100644 --- a/src/core/CMakeLists.txt +++ b/src/core/CMakeLists.txt | |||
| @@ -172,6 +172,7 @@ add_library(core STATIC | |||
| 172 | hle/kernel/k_memory_layout.h | 172 | hle/kernel/k_memory_layout.h |
| 173 | hle/kernel/k_memory_manager.cpp | 173 | hle/kernel/k_memory_manager.cpp |
| 174 | hle/kernel/k_memory_manager.h | 174 | hle/kernel/k_memory_manager.h |
| 175 | hle/kernel/k_memory_region.h | ||
| 175 | hle/kernel/k_page_bitmap.h | 176 | hle/kernel/k_page_bitmap.h |
| 176 | hle/kernel/k_page_heap.cpp | 177 | hle/kernel/k_page_heap.cpp |
| 177 | hle/kernel/k_page_heap.h | 178 | hle/kernel/k_page_heap.h |
diff --git a/src/core/hle/kernel/k_memory_layout.h b/src/core/hle/kernel/k_memory_layout.h index 0821d2d8c..a76ffa02e 100644 --- a/src/core/hle/kernel/k_memory_layout.h +++ b/src/core/hle/kernel/k_memory_layout.h | |||
| @@ -6,6 +6,7 @@ | |||
| 6 | 6 | ||
| 7 | #include "common/common_types.h" | 7 | #include "common/common_types.h" |
| 8 | #include "core/device_memory.h" | 8 | #include "core/device_memory.h" |
| 9 | #include "core/hle/kernel/k_memory_region.h" | ||
| 9 | 10 | ||
| 10 | namespace Kernel { | 11 | namespace Kernel { |
| 11 | 12 | ||
| @@ -27,27 +28,6 @@ constexpr bool IsKernelAddress(VAddr address) { | |||
| 27 | return KernelVirtualAddressSpaceBase <= address && address < KernelVirtualAddressSpaceEnd; | 28 | return KernelVirtualAddressSpaceBase <= address && address < KernelVirtualAddressSpaceEnd; |
| 28 | } | 29 | } |
| 29 | 30 | ||
| 30 | class KMemoryRegion final { | ||
| 31 | friend class KMemoryLayout; | ||
| 32 | |||
| 33 | public: | ||
| 34 | constexpr PAddr StartAddress() const { | ||
| 35 | return start_address; | ||
| 36 | } | ||
| 37 | |||
| 38 | constexpr PAddr EndAddress() const { | ||
| 39 | return end_address; | ||
| 40 | } | ||
| 41 | |||
| 42 | private: | ||
| 43 | constexpr KMemoryRegion() = default; | ||
| 44 | constexpr KMemoryRegion(PAddr start_address, PAddr end_address) | ||
| 45 | : start_address{start_address}, end_address{end_address} {} | ||
| 46 | |||
| 47 | const PAddr start_address{}; | ||
| 48 | const PAddr end_address{}; | ||
| 49 | }; | ||
| 50 | |||
| 51 | class KMemoryLayout final { | 31 | class KMemoryLayout final { |
| 52 | public: | 32 | public: |
| 53 | constexpr const KMemoryRegion& Application() const { | 33 | constexpr const KMemoryRegion& Application() const { |
diff --git a/src/core/hle/kernel/k_memory_region.h b/src/core/hle/kernel/k_memory_region.h new file mode 100644 index 000000000..de236df6a --- /dev/null +++ b/src/core/hle/kernel/k_memory_region.h | |||
| @@ -0,0 +1,310 @@ | |||
| 1 | // Copyright 2021 yuzu Emulator Project | ||
| 2 | // Licensed under GPLv2 or any later version | ||
| 3 | // Refer to the license.txt file included. | ||
| 4 | |||
| 5 | #pragma once | ||
| 6 | |||
| 7 | #include "common/assert.h" | ||
| 8 | #include "common/common_types.h" | ||
| 9 | #include "common/intrusive_red_black_tree.h" | ||
| 10 | |||
| 11 | namespace Kernel { | ||
| 12 | |||
| 13 | class KMemoryRegion final : public Common::IntrusiveRedBlackTreeBaseNode<KMemoryRegion>, | ||
| 14 | NonCopyable { | ||
| 15 | friend class KMemoryLayout; | ||
| 16 | friend class KMemoryRegionTree; | ||
| 17 | |||
| 18 | public: | ||
| 19 | static constexpr int Compare(const KMemoryRegion& lhs, const KMemoryRegion& rhs) { | ||
| 20 | if (lhs.GetAddress() < rhs.GetAddress()) { | ||
| 21 | return -1; | ||
| 22 | } else if (lhs.GetAddress() <= rhs.GetLastAddress()) { | ||
| 23 | return 0; | ||
| 24 | } else { | ||
| 25 | return 1; | ||
| 26 | } | ||
| 27 | } | ||
| 28 | |||
| 29 | constexpr u64 GetAddress() const { | ||
| 30 | return address; | ||
| 31 | } | ||
| 32 | |||
| 33 | constexpr u64 GetPairAddress() const { | ||
| 34 | return pair_address; | ||
| 35 | } | ||
| 36 | |||
| 37 | constexpr u64 GetLastAddress() const { | ||
| 38 | return last_address; | ||
| 39 | } | ||
| 40 | |||
| 41 | constexpr u64 GetEndAddress() const { | ||
| 42 | return GetLastAddress() + 1; | ||
| 43 | } | ||
| 44 | |||
| 45 | constexpr std::size_t GetSize() const { | ||
| 46 | return GetEndAddress() - GetAddress(); | ||
| 47 | } | ||
| 48 | |||
| 49 | constexpr u32 GetAttributes() const { | ||
| 50 | return attributes; | ||
| 51 | } | ||
| 52 | |||
| 53 | constexpr u32 GetType() const { | ||
| 54 | return type_id; | ||
| 55 | } | ||
| 56 | |||
| 57 | constexpr void SetType(u32 type) { | ||
| 58 | ASSERT(this->CanDerive(type)); | ||
| 59 | type_id = type; | ||
| 60 | } | ||
| 61 | |||
| 62 | constexpr bool Contains(uintptr_t address) const { | ||
| 63 | ASSERT(this->GetEndAddress() != 0); | ||
| 64 | return this->GetAddress() <= address && address <= this->GetLastAddress(); | ||
| 65 | } | ||
| 66 | |||
| 67 | constexpr bool IsDerivedFrom(u32 type) const { | ||
| 68 | return (this->GetType() | type) == this->GetType(); | ||
| 69 | } | ||
| 70 | |||
| 71 | // constexpr bool HasTypeAttribute(KMemoryRegionAttr attr) const { | ||
| 72 | // return (this->GetType() | attr) == this->GetType(); | ||
| 73 | //} | ||
| 74 | |||
| 75 | constexpr bool CanDerive(u32 type) const { | ||
| 76 | return (this->GetType() | type) == type; | ||
| 77 | } | ||
| 78 | |||
| 79 | constexpr void SetPairAddress(u64 a) { | ||
| 80 | pair_address = a; | ||
| 81 | } | ||
| 82 | |||
| 83 | // constexpr void SetTypeAttribute(KMemoryRegionAttr attr) { | ||
| 84 | // type_id |= attr; | ||
| 85 | //} | ||
| 86 | |||
| 87 | private: | ||
| 88 | constexpr KMemoryRegion() = default; | ||
| 89 | constexpr KMemoryRegion(u64 address_, u64 last_address_) | ||
| 90 | : address{address_}, last_address{last_address_} {} | ||
| 91 | constexpr KMemoryRegion(u64 address_, u64 last_address_, u64 pair_address_, u32 attributes_, | ||
| 92 | u32 type_id_) | ||
| 93 | : address(address_), last_address(last_address_), pair_address(pair_address_), | ||
| 94 | attributes(attributes_), type_id(type_id_) {} | ||
| 95 | constexpr KMemoryRegion(u64 address_, u64 last_address_, u32 attributes_, u32 type_id_) | ||
| 96 | : KMemoryRegion(address_, last_address_, std::numeric_limits<uintptr_t>::max(), attributes_, | ||
| 97 | type_id_) {} | ||
| 98 | |||
| 99 | const u64 address{}; | ||
| 100 | const u64 last_address{}; | ||
| 101 | u64 pair_address{}; | ||
| 102 | u32 attributes{}; | ||
| 103 | u32 type_id{}; | ||
| 104 | }; | ||
| 105 | |||
| 106 | class KMemoryRegionTree final : NonCopyable { | ||
| 107 | public: | ||
| 108 | struct DerivedRegionExtents { | ||
| 109 | const KMemoryRegion* first_region{}; | ||
| 110 | const KMemoryRegion* last_region{}; | ||
| 111 | |||
| 112 | constexpr DerivedRegionExtents() = default; | ||
| 113 | |||
| 114 | constexpr u64 GetAddress() const { | ||
| 115 | return this->first_region->GetAddress(); | ||
| 116 | } | ||
| 117 | |||
| 118 | constexpr u64 GetLastAddress() const { | ||
| 119 | return this->last_region->GetLastAddress(); | ||
| 120 | } | ||
| 121 | |||
| 122 | constexpr u64 GetEndAddress() const { | ||
| 123 | return this->GetLastAddress() + 1; | ||
| 124 | } | ||
| 125 | |||
| 126 | constexpr size_t GetSize() const { | ||
| 127 | return this->GetEndAddress() - this->GetAddress(); | ||
| 128 | } | ||
| 129 | }; | ||
| 130 | |||
| 131 | private: | ||
| 132 | using TreeType = | ||
| 133 | Common::IntrusiveRedBlackTreeBaseTraits<KMemoryRegion>::TreeType<KMemoryRegion>; | ||
| 134 | |||
| 135 | public: | ||
| 136 | using value_type = TreeType::value_type; | ||
| 137 | using size_type = TreeType::size_type; | ||
| 138 | using difference_type = TreeType::difference_type; | ||
| 139 | using pointer = TreeType::pointer; | ||
| 140 | using const_pointer = TreeType::const_pointer; | ||
| 141 | using reference = TreeType::reference; | ||
| 142 | using const_reference = TreeType::const_reference; | ||
| 143 | using iterator = TreeType::iterator; | ||
| 144 | using const_iterator = TreeType::const_iterator; | ||
| 145 | |||
| 146 | private: | ||
| 147 | TreeType m_tree{}; | ||
| 148 | |||
| 149 | public: | ||
| 150 | constexpr KMemoryRegionTree() = default; | ||
| 151 | |||
| 152 | public: | ||
| 153 | KMemoryRegion* FindModifiable(u64 address) { | ||
| 154 | if (auto it = this->find(KMemoryRegion(address, address, 0, 0)); it != this->end()) { | ||
| 155 | return std::addressof(*it); | ||
| 156 | } else { | ||
| 157 | return nullptr; | ||
| 158 | } | ||
| 159 | } | ||
| 160 | |||
| 161 | const KMemoryRegion* Find(u64 address) const { | ||
| 162 | if (auto it = this->find(KMemoryRegion(address, address, 0, 0)); it != this->cend()) { | ||
| 163 | return std::addressof(*it); | ||
| 164 | } else { | ||
| 165 | return nullptr; | ||
| 166 | } | ||
| 167 | } | ||
| 168 | |||
| 169 | const KMemoryRegion* FindByType(u32 type_id) const { | ||
| 170 | for (auto it = this->cbegin(); it != this->cend(); ++it) { | ||
| 171 | if (it->GetType() == type_id) { | ||
| 172 | return std::addressof(*it); | ||
| 173 | } | ||
| 174 | } | ||
| 175 | return nullptr; | ||
| 176 | } | ||
| 177 | |||
| 178 | const KMemoryRegion* FindByTypeAndAttribute(u32 type_id, u32 attr) const { | ||
| 179 | for (auto it = this->cbegin(); it != this->cend(); ++it) { | ||
| 180 | if (it->GetType() == type_id && it->GetAttributes() == attr) { | ||
| 181 | return std::addressof(*it); | ||
| 182 | } | ||
| 183 | } | ||
| 184 | return nullptr; | ||
| 185 | } | ||
| 186 | |||
| 187 | const KMemoryRegion* FindFirstDerived(u32 type_id) const { | ||
| 188 | for (auto it = this->cbegin(); it != this->cend(); it++) { | ||
| 189 | if (it->IsDerivedFrom(type_id)) { | ||
| 190 | return std::addressof(*it); | ||
| 191 | } | ||
| 192 | } | ||
| 193 | return nullptr; | ||
| 194 | } | ||
| 195 | |||
| 196 | const KMemoryRegion* FindLastDerived(u32 type_id) const { | ||
| 197 | const KMemoryRegion* region = nullptr; | ||
| 198 | for (auto it = this->begin(); it != this->end(); it++) { | ||
| 199 | if (it->IsDerivedFrom(type_id)) { | ||
| 200 | region = std::addressof(*it); | ||
| 201 | } | ||
| 202 | } | ||
| 203 | return region; | ||
| 204 | } | ||
| 205 | |||
| 206 | DerivedRegionExtents GetDerivedRegionExtents(u32 type_id) const { | ||
| 207 | DerivedRegionExtents extents; | ||
| 208 | |||
| 209 | ASSERT(extents.first_region == nullptr); | ||
| 210 | ASSERT(extents.last_region == nullptr); | ||
| 211 | |||
| 212 | for (auto it = this->cbegin(); it != this->cend(); it++) { | ||
| 213 | if (it->IsDerivedFrom(type_id)) { | ||
| 214 | if (extents.first_region == nullptr) { | ||
| 215 | extents.first_region = std::addressof(*it); | ||
| 216 | } | ||
| 217 | extents.last_region = std::addressof(*it); | ||
| 218 | } | ||
| 219 | } | ||
| 220 | |||
| 221 | ASSERT(extents.first_region != nullptr); | ||
| 222 | ASSERT(extents.last_region != nullptr); | ||
| 223 | |||
| 224 | return extents; | ||
| 225 | } | ||
| 226 | |||
| 227 | public: | ||
| 228 | void InsertDirectly(u64 address, u64 last_address, u32 attr = 0, u32 type_id = 0); | ||
| 229 | bool Insert(u64 address, size_t size, u32 type_id, u32 new_attr = 0, u32 old_attr = 0); | ||
| 230 | |||
| 231 | VAddr GetRandomAlignedRegion(size_t size, size_t alignment, u32 type_id); | ||
| 232 | |||
| 233 | VAddr GetRandomAlignedRegionWithGuard(size_t size, size_t alignment, u32 type_id, | ||
| 234 | size_t guard_size) { | ||
| 235 | return this->GetRandomAlignedRegion(size + 2 * guard_size, alignment, type_id) + guard_size; | ||
| 236 | } | ||
| 237 | |||
| 238 | public: | ||
| 239 | // Iterator accessors. | ||
| 240 | iterator begin() { | ||
| 241 | return m_tree.begin(); | ||
| 242 | } | ||
| 243 | |||
| 244 | const_iterator begin() const { | ||
| 245 | return m_tree.begin(); | ||
| 246 | } | ||
| 247 | |||
| 248 | iterator end() { | ||
| 249 | return m_tree.end(); | ||
| 250 | } | ||
| 251 | |||
| 252 | const_iterator end() const { | ||
| 253 | return m_tree.end(); | ||
| 254 | } | ||
| 255 | |||
| 256 | const_iterator cbegin() const { | ||
| 257 | return this->begin(); | ||
| 258 | } | ||
| 259 | |||
| 260 | const_iterator cend() const { | ||
| 261 | return this->end(); | ||
| 262 | } | ||
| 263 | |||
| 264 | iterator iterator_to(reference ref) { | ||
| 265 | return m_tree.iterator_to(ref); | ||
| 266 | } | ||
| 267 | |||
| 268 | const_iterator iterator_to(const_reference ref) const { | ||
| 269 | return m_tree.iterator_to(ref); | ||
| 270 | } | ||
| 271 | |||
| 272 | // Content management. | ||
| 273 | bool empty() const { | ||
| 274 | return m_tree.empty(); | ||
| 275 | } | ||
| 276 | |||
| 277 | reference back() { | ||
| 278 | return m_tree.back(); | ||
| 279 | } | ||
| 280 | |||
| 281 | const_reference back() const { | ||
| 282 | return m_tree.back(); | ||
| 283 | } | ||
| 284 | |||
| 285 | reference front() { | ||
| 286 | return m_tree.front(); | ||
| 287 | } | ||
| 288 | |||
| 289 | const_reference front() const { | ||
| 290 | return m_tree.front(); | ||
| 291 | } | ||
| 292 | |||
| 293 | iterator insert(reference ref) { | ||
| 294 | return m_tree.insert(ref); | ||
| 295 | } | ||
| 296 | |||
| 297 | iterator erase(iterator it) { | ||
| 298 | return m_tree.erase(it); | ||
| 299 | } | ||
| 300 | |||
| 301 | iterator find(const_reference ref) const { | ||
| 302 | return m_tree.find(ref); | ||
| 303 | } | ||
| 304 | |||
| 305 | iterator nfind(const_reference ref) const { | ||
| 306 | return m_tree.nfind(ref); | ||
| 307 | } | ||
| 308 | }; | ||
| 309 | |||
| 310 | } // namespace Kernel | ||
diff --git a/src/core/hle/kernel/kernel.cpp b/src/core/hle/kernel/kernel.cpp index 780008b08..48916df17 100644 --- a/src/core/hle/kernel/kernel.cpp +++ b/src/core/hle/kernel/kernel.cpp | |||
| @@ -275,22 +275,22 @@ struct KernelCore::Impl { | |||
| 275 | constexpr std::size_t font_size{0x1100000}; | 275 | constexpr std::size_t font_size{0x1100000}; |
| 276 | constexpr std::size_t irs_size{0x8000}; | 276 | constexpr std::size_t irs_size{0x8000}; |
| 277 | constexpr std::size_t time_size{0x1000}; | 277 | constexpr std::size_t time_size{0x1000}; |
| 278 | constexpr PAddr hid_addr{layout.System().StartAddress()}; | 278 | constexpr PAddr hid_addr{layout.System().GetAddress()}; |
| 279 | constexpr PAddr font_pa{layout.System().StartAddress() + hid_size}; | 279 | constexpr PAddr font_pa{layout.System().GetAddress() + hid_size}; |
| 280 | constexpr PAddr irs_addr{layout.System().StartAddress() + hid_size + font_size}; | 280 | constexpr PAddr irs_addr{layout.System().GetAddress() + hid_size + font_size}; |
| 281 | constexpr PAddr time_addr{layout.System().StartAddress() + hid_size + font_size + irs_size}; | 281 | constexpr PAddr time_addr{layout.System().GetAddress() + hid_size + font_size + irs_size}; |
| 282 | 282 | ||
| 283 | // Initialize memory manager | 283 | // Initialize memory manager |
| 284 | memory_manager = std::make_unique<KMemoryManager>(); | 284 | memory_manager = std::make_unique<KMemoryManager>(); |
| 285 | memory_manager->InitializeManager(KMemoryManager::Pool::Application, | 285 | memory_manager->InitializeManager(KMemoryManager::Pool::Application, |
| 286 | layout.Application().StartAddress(), | 286 | layout.Application().GetAddress(), |
| 287 | layout.Application().EndAddress()); | 287 | layout.Application().GetLastAddress()); |
| 288 | memory_manager->InitializeManager(KMemoryManager::Pool::Applet, | 288 | memory_manager->InitializeManager(KMemoryManager::Pool::Applet, |
| 289 | layout.Applet().StartAddress(), | 289 | layout.Applet().GetAddress(), |
| 290 | layout.Applet().EndAddress()); | 290 | layout.Applet().GetLastAddress()); |
| 291 | memory_manager->InitializeManager(KMemoryManager::Pool::System, | 291 | memory_manager->InitializeManager(KMemoryManager::Pool::System, |
| 292 | layout.System().StartAddress(), | 292 | layout.System().GetAddress(), |
| 293 | layout.System().EndAddress()); | 293 | layout.System().GetLastAddress()); |
| 294 | 294 | ||
| 295 | hid_shared_mem = Kernel::KSharedMemory::Create( | 295 | hid_shared_mem = Kernel::KSharedMemory::Create( |
| 296 | system.Kernel(), system.DeviceMemory(), nullptr, {hid_addr, hid_size / PageSize}, | 296 | system.Kernel(), system.DeviceMemory(), nullptr, {hid_addr, hid_size / PageSize}, |