mirror of
				https://github.com/PabloMK7/citra.git
				synced 2025-10-31 13:50:03 +00:00 
			
		
		
		
	Res cache fixes (#6838)
* rasterizer_cache: Dont consider res_scale during recycle * rasterizer_cache: Switch to plain erase loop * rasterizer_cache: Fix crash due to memory corruption
This commit is contained in:
		
							parent
							
								
									88ea66053e
								
							
						
					
					
						commit
						6f7612f73d
					
				
					 3 changed files with 26 additions and 17 deletions
				
			
		|  | @ -1051,15 +1051,15 @@ bool RasterizerCache<T>::UploadCustomSurface(SurfaceId surface_id, SurfaceInterv | ||||||
|     surface.flags |= SurfaceFlagBits::Custom; |     surface.flags |= SurfaceFlagBits::Custom; | ||||||
| 
 | 
 | ||||||
|     const auto upload = [this, level, surface_id, material]() -> bool { |     const auto upload = [this, level, surface_id, material]() -> bool { | ||||||
|         Surface& surface = slot_surfaces[surface_id]; |         ASSERT_MSG(True(slot_surfaces[surface_id].flags & SurfaceFlagBits::Custom), | ||||||
|         ASSERT_MSG(True(surface.flags & SurfaceFlagBits::Custom), |  | ||||||
|                    "Surface is not suitable for custom upload, aborting!"); |                    "Surface is not suitable for custom upload, aborting!"); | ||||||
|         if (!surface.IsCustom()) { |         if (!slot_surfaces[surface_id].IsCustom()) { | ||||||
|             const SurfaceBase old_surface{surface}; |             const SurfaceBase old_surface{slot_surfaces[surface_id]}; | ||||||
|             const SurfaceId old_id = |             const SurfaceId old_id = | ||||||
|                 slot_surfaces.swap_and_insert(surface_id, runtime, old_surface, material); |                 slot_surfaces.swap_and_insert(surface_id, runtime, old_surface, material); | ||||||
|             sentenced.emplace_back(old_id, frame_tick); |             sentenced.emplace_back(old_id, frame_tick); | ||||||
|         } |         } | ||||||
|  |         Surface& surface = slot_surfaces[surface_id]; | ||||||
|         surface.UploadCustom(material, level); |         surface.UploadCustom(material, level); | ||||||
|         if (custom_tex_manager.SkipMipmaps()) { |         if (custom_tex_manager.SkipMipmaps()) { | ||||||
|             runtime.GenerateMipmaps(surface); |             runtime.GenerateMipmaps(surface); | ||||||
|  | @ -1316,14 +1316,17 @@ SurfaceId RasterizerCache<T>::CreateSurface(const SurfaceParams& params) { | ||||||
|         const auto it = std::find_if(sentenced.begin(), sentenced.end(), [&](const auto& pair) { |         const auto it = std::find_if(sentenced.begin(), sentenced.end(), [&](const auto& pair) { | ||||||
|             return slot_surfaces[pair.first] == params; |             return slot_surfaces[pair.first] == params; | ||||||
|         }); |         }); | ||||||
|         if (it != sentenced.end()) { |         if (it == sentenced.end()) { | ||||||
|             const SurfaceId surface_id = it->first; |             return slot_surfaces.insert(runtime, params); | ||||||
|             sentenced.erase(it); |  | ||||||
|             return surface_id; |  | ||||||
|         } |         } | ||||||
|         return slot_surfaces.insert(runtime, params); |         const SurfaceId surface_id = it->first; | ||||||
|  |         sentenced.erase(it); | ||||||
|  |         return surface_id; | ||||||
|     }(); |     }(); | ||||||
|     Surface& surface = slot_surfaces[surface_id]; |     Surface& surface = slot_surfaces[surface_id]; | ||||||
|  |     if (params.res_scale > surface.res_scale) { | ||||||
|  |         surface.ScaleUp(params.res_scale); | ||||||
|  |     } | ||||||
|     surface.MarkInvalid(surface.GetInterval()); |     surface.MarkInvalid(surface.GetInterval()); | ||||||
|     return surface_id; |     return surface_id; | ||||||
| } | } | ||||||
|  | @ -1368,8 +1371,8 @@ void RasterizerCache<T>::UnregisterSurface(SurfaceId surface_id) { | ||||||
|         return; |         return; | ||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|     std::erase_if(texture_cube_cache, [&](auto& pair) { |     for (auto it = texture_cube_cache.begin(); it != texture_cube_cache.end();) { | ||||||
|         TextureCube& cube = pair.second; |         TextureCube& cube = it->second; | ||||||
|         for (SurfaceId& face_id : cube.face_ids) { |         for (SurfaceId& face_id : cube.face_ids) { | ||||||
|             if (face_id == surface_id) { |             if (face_id == surface_id) { | ||||||
|                 face_id = SurfaceId{}; |                 face_id = SurfaceId{}; | ||||||
|  | @ -1378,10 +1381,11 @@ void RasterizerCache<T>::UnregisterSurface(SurfaceId surface_id) { | ||||||
|         if (std::none_of(cube.face_ids.begin(), cube.face_ids.end(), |         if (std::none_of(cube.face_ids.begin(), cube.face_ids.end(), | ||||||
|                          [](SurfaceId id) { return id; })) { |                          [](SurfaceId id) { return id; })) { | ||||||
|             sentenced.emplace_back(cube.surface_id, frame_tick); |             sentenced.emplace_back(cube.surface_id, frame_tick); | ||||||
|             return true; |             it = texture_cube_cache.erase(it); | ||||||
|  |         } else { | ||||||
|  |             it++; | ||||||
|         } |         } | ||||||
|         return false; |     } | ||||||
|     }); |  | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| template <class T> | template <class T> | ||||||
|  |  | ||||||
|  | @ -227,4 +227,11 @@ std::string SurfaceParams::DebugName(bool scaled, bool custom) const noexcept { | ||||||
|                        custom ? "custom," : "", scaled ? "scaled" : "unscaled"); |                        custom ? "custom," : "", scaled ? "scaled" : "unscaled"); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | bool SurfaceParams::operator==(const SurfaceParams& other) const noexcept { | ||||||
|  |     return std::tie(addr, end, width, height, stride, levels, is_tiled, texture_type, pixel_format, | ||||||
|  |                     custom_format) == | ||||||
|  |            std::tie(other.addr, other.end, other.width, other.height, other.stride, other.levels, | ||||||
|  |                     other.is_tiled, other.texture_type, other.pixel_format, other.custom_format); | ||||||
|  | } | ||||||
|  | 
 | ||||||
| } // namespace VideoCore
 | } // namespace VideoCore
 | ||||||
|  |  | ||||||
|  | @ -53,9 +53,7 @@ public: | ||||||
|     /// Returns a string identifier of the params object
 |     /// Returns a string identifier of the params object
 | ||||||
|     std::string DebugName(bool scaled, bool custom = false) const noexcept; |     std::string DebugName(bool scaled, bool custom = false) const noexcept; | ||||||
| 
 | 
 | ||||||
|     bool operator==(const SurfaceParams& other) const noexcept { |     bool operator==(const SurfaceParams& other) const noexcept; | ||||||
|         return std::memcmp(this, &other, sizeof(SurfaceParams)) == 0; |  | ||||||
|     } |  | ||||||
| 
 | 
 | ||||||
|     [[nodiscard]] SurfaceInterval GetInterval() const noexcept { |     [[nodiscard]] SurfaceInterval GetInterval() const noexcept { | ||||||
|         return SurfaceInterval{addr, end}; |         return SurfaceInterval{addr, end}; | ||||||
|  |  | ||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue