diff options
| author | Takoroka <137927095+Takoroka@users.noreply.github.com> | 2026-11-01 13:25:46 -0500 |
|---|---|---|
| committer | Takoroka <137927095+Takoroka@users.noreply.github.com> | 2026-11-01 13:25:46 -0500 |
| commit | 9ee8d6f6a6900537eccf67e4c3a9bb16248dc6ab (patch) | |
| tree | 66082e3914f210cfdcb144c67e98a3aa16b5b5b4 /src/core/device_memory_manager.inc | |
| parent | f695266b80ba1e8a4a4f2f8421d65ed224068c7a (diff) | |
| parent | 86968cb5ce3195cb131eeb0ef68d2d8a4860f7df (diff) | |
Merge remote-tracking branch 'origin/fix/cold-hint-uploaded-memory' into test/linux-all-prs
Diffstat (limited to 'src/core/device_memory_manager.inc')
| -rw-r--r-- | src/core/device_memory_manager.inc | 44 |
1 files changed, 44 insertions, 0 deletions
diff --git a/src/core/device_memory_manager.inc b/src/core/device_memory_manager.inc index 83faa1b3f3..3523e3cf1c 100644 --- a/src/core/device_memory_manager.inc +++ b/src/core/device_memory_manager.inc @@ -171,6 +171,7 @@ struct DeviceMemoryManagerAllocator { template <typename Traits> DeviceMemoryManager<Traits>::DeviceMemoryManager(const DeviceMemory& device_memory_) : physical_base{uintptr_t(device_memory_.buffer.BackingBasePointer())} + , device_memory_ptr{&device_memory_} , device_inter{nullptr} , compressed_device_addr(1ULL << ((Settings::values.memory_layout_mode.GetValue() == Settings::MemoryLayout::Memory_4Gb ? physical_min_bits : physical_max_bits) - Memory::YUZU_PAGEBITS)) , tracked_entries(device_as_size >> Memory::YUZU_PAGEBITS) @@ -183,6 +184,49 @@ template <typename Traits> DeviceMemoryManager<Traits>::~DeviceMemoryManager() = default; template <typename Traits> +void DeviceMemoryManager<Traits>::HintCold(DAddr address, size_t size) { + struct Run { + u64 physical_offset; + VAddr virtual_address; ///< 0: no CPU mapping known + u64 size; + }; + std::vector<Run> runs; + const size_t page_end = Common::DivCeil(address + size, Memory::YUZU_PAGESIZE); + for (size_t page = address >> Memory::YUZU_PAGEBITS; page < page_end; ++page) { + const u32 compressed = tracked_entries[page].compressed_physical_ptr; + if (compressed == 0) { + continue; + } + const u64 physical = u64{compressed - 1} << Memory::YUZU_PAGEBITS; + const VAddr vaddr = ExtractCPUBacking(page).second; + if (!runs.empty()) { + Run& last = runs.back(); + const bool contiguous_view = + last.virtual_address == 0 ? vaddr == 0 : last.virtual_address + last.size == vaddr; + if (last.physical_offset + last.size == physical && contiguous_view) { + last.size += Memory::YUZU_PAGESIZE; + continue; + } + } + runs.push_back({physical, vaddr, Memory::YUZU_PAGESIZE}); + } + if (runs.empty()) { + return; + } + if (!cold_hint_worker) { + cold_hint_worker = std::make_unique<Common::ThreadWorker>(1, "DeviceMemory:ColdHint"); + } + cold_hint_worker->QueueWork([this, runs = std::move(runs)] { + for (const Run& run : runs) { + device_memory_ptr->buffer.HintCold( + run.physical_offset, run.size, + run.virtual_address != 0 ? std::optional<size_t>{run.virtual_address} + : std::nullopt); + } + }); +} + +template <typename Traits> void DeviceMemoryManager<Traits>::BindInterface(DeviceInterface* device_inter_) { device_inter = device_inter_; } |
