mirror of
				https://git.zaroz.cloud/nintendo-back-up/yuzu/yuzu.git
				synced 2025-05-12 00:45:25 +00:00 
			
		
		
		
	gl_rasterizer: Implement AccelerateDisplay to forward textures to framebuffers.
This commit is contained in:
		
							parent
							
								
									ff6785f3e8
								
							
						
					
					
						commit
						3f9f047375
					
				| @ -51,9 +51,8 @@ public: | |||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|     /// Attempt to use a faster method to display the framebuffer to screen
 |     /// Attempt to use a faster method to display the framebuffer to screen
 | ||||||
|     virtual bool AccelerateDisplay(const Tegra::FramebufferConfig& framebuffer, |     virtual bool AccelerateDisplay(const Tegra::FramebufferConfig& config, VAddr framebuffer_addr, | ||||||
|                                    VAddr framebuffer_addr, u32 pixel_stride, |                                    u32 pixel_stride, ScreenInfo& screen_info) { | ||||||
|                                    ScreenInfo& screen_info) { |  | ||||||
|         return false; |         return false; | ||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|  | |||||||
| @ -468,11 +468,30 @@ bool RasterizerOpenGL::AccelerateFill(const void* config) { | |||||||
|     return true; |     return true; | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| bool RasterizerOpenGL::AccelerateDisplay(const Tegra::FramebufferConfig& framebuffer, | bool RasterizerOpenGL::AccelerateDisplay(const Tegra::FramebufferConfig& config, | ||||||
|                                          VAddr framebuffer_addr, u32 pixel_stride, |                                          VAddr framebuffer_addr, u32 pixel_stride, | ||||||
|                                          ScreenInfo& screen_info) { |                                          ScreenInfo& screen_info) { | ||||||
|     // TODO(bunnei): ImplementMe
 |     if (!framebuffer_addr) { | ||||||
|     return false; |         return {}; | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     MICROPROFILE_SCOPE(OpenGL_CacheManagement); | ||||||
|  | 
 | ||||||
|  |     const auto& surface{res_cache.TryFindFramebufferSurface(framebuffer_addr)}; | ||||||
|  |     if (!surface) { | ||||||
|  |         return {}; | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     // Verify that the cached surface is the same size and format as the requested framebuffer
 | ||||||
|  |     const auto& params{surface->GetSurfaceParams()}; | ||||||
|  |     const auto& pixel_format{SurfaceParams::PixelFormatFromGPUPixelFormat(config.pixel_format)}; | ||||||
|  |     ASSERT_MSG(params.width == config.width, "Framebuffer width is different"); | ||||||
|  |     ASSERT_MSG(params.height == config.height, "Framebuffer height is different"); | ||||||
|  |     ASSERT_MSG(params.pixel_format == pixel_format, "Framebuffer pixel_format is different"); | ||||||
|  | 
 | ||||||
|  |     screen_info.display_texture = surface->Texture().handle; | ||||||
|  | 
 | ||||||
|  |     return true; | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| void RasterizerOpenGL::SamplerInfo::Create() { | void RasterizerOpenGL::SamplerInfo::Create() { | ||||||
|  | |||||||
| @ -436,3 +436,29 @@ Surface RasterizerCacheOpenGL::GetSurface(const SurfaceParams& params) { | |||||||
| 
 | 
 | ||||||
|     return surface; |     return surface; | ||||||
| } | } | ||||||
|  | 
 | ||||||
|  | Surface RasterizerCacheOpenGL::TryFindFramebufferSurface(VAddr cpu_addr) const { | ||||||
|  |     // Tries to find the GPU address of a framebuffer based on the CPU address. This is because
 | ||||||
|  |     // final output framebuffers are specified by CPU address, but internally our GPU cache uses GPU
 | ||||||
|  |     // addresses. We iterate through all cached framebuffers, and compare their starting CPU address
 | ||||||
|  |     // to the one provided. This is obviously not great, and won't work if the framebuffer overlaps
 | ||||||
|  |     // surfaces.
 | ||||||
|  | 
 | ||||||
|  |     std::vector<Surface> surfaces; | ||||||
|  |     for (const auto& surface : surface_cache) { | ||||||
|  |         const auto& params = surface.second->GetSurfaceParams(); | ||||||
|  |         const VAddr surface_cpu_addr = params.GetCpuAddr(); | ||||||
|  |         if (cpu_addr >= surface_cpu_addr && cpu_addr < (surface_cpu_addr + params.size_in_bytes)) { | ||||||
|  |             ASSERT_MSG(cpu_addr == surface_cpu_addr, "overlapping surfaces are unsupported"); | ||||||
|  |             surfaces.push_back(surface.second); | ||||||
|  |         } | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     if (surfaces.empty()) { | ||||||
|  |         return {}; | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     ASSERT_MSG(surfaces.size() == 1, ">1 surface is unsupported"); | ||||||
|  | 
 | ||||||
|  |     return surfaces[0]; | ||||||
|  | } | ||||||
|  | |||||||
| @ -220,6 +220,16 @@ struct SurfaceParams { | |||||||
|         } |         } | ||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|  |     static PixelFormat PixelFormatFromGPUPixelFormat(Tegra::FramebufferConfig::PixelFormat format) { | ||||||
|  |         switch (format) { | ||||||
|  |         case Tegra::FramebufferConfig::PixelFormat::ABGR8: | ||||||
|  |             return PixelFormat::ABGR8; | ||||||
|  |         default: | ||||||
|  |             NGLOG_CRITICAL(HW_GPU, "Unimplemented format={}", static_cast<u32>(format)); | ||||||
|  |             UNREACHABLE(); | ||||||
|  |         } | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|     static SurfaceType GetFormatType(PixelFormat pixel_format) { |     static SurfaceType GetFormatType(PixelFormat pixel_format) { | ||||||
|         if (static_cast<size_t>(pixel_format) < MaxPixelFormat) { |         if (static_cast<size_t>(pixel_format) < MaxPixelFormat) { | ||||||
|             return SurfaceType::ColorTexture; |             return SurfaceType::ColorTexture; | ||||||
| @ -302,6 +312,7 @@ public: | |||||||
|                                                     const MathUtil::Rectangle<s32>& viewport); |                                                     const MathUtil::Rectangle<s32>& viewport); | ||||||
|     void LoadSurface(const Surface& surface); |     void LoadSurface(const Surface& surface); | ||||||
|     void FlushSurface(const Surface& surface); |     void FlushSurface(const Surface& surface); | ||||||
|  |     Surface TryFindFramebufferSurface(VAddr cpu_addr) const; | ||||||
| 
 | 
 | ||||||
| private: | private: | ||||||
|     Surface GetSurface(const SurfaceParams& params); |     Surface GetSurface(const SurfaceParams& params); | ||||||
|  | |||||||
| @ -150,7 +150,6 @@ void RendererOpenGL::LoadFBToScreenInfo(const Tegra::FramebufferConfig& framebuf | |||||||
|                                          screen_info)) { |                                          screen_info)) { | ||||||
|         // Reset the screen info's display texture to its own permanent texture
 |         // Reset the screen info's display texture to its own permanent texture
 | ||||||
|         screen_info.display_texture = screen_info.texture.resource.handle; |         screen_info.display_texture = screen_info.texture.resource.handle; | ||||||
|         screen_info.display_texcoords = MathUtil::Rectangle<float>(0.f, 0.f, 1.f, 1.f); |  | ||||||
| 
 | 
 | ||||||
|         Memory::RasterizerFlushVirtualRegion(framebuffer_addr, size_in_bytes, |         Memory::RasterizerFlushVirtualRegion(framebuffer_addr, size_in_bytes, | ||||||
|                                              Memory::FlushMode::Flush); |                                              Memory::FlushMode::Flush); | ||||||
|  | |||||||
| @ -27,7 +27,7 @@ struct TextureInfo { | |||||||
| /// Structure used for storing information about the display target for the Switch screen
 | /// Structure used for storing information about the display target for the Switch screen
 | ||||||
| struct ScreenInfo { | struct ScreenInfo { | ||||||
|     GLuint display_texture; |     GLuint display_texture; | ||||||
|     MathUtil::Rectangle<float> display_texcoords; |     const MathUtil::Rectangle<float> display_texcoords{0.0f, 0.0f, 1.0f, 1.0f}; | ||||||
|     TextureInfo texture; |     TextureInfo texture; | ||||||
| }; | }; | ||||||
| 
 | 
 | ||||||
|  | |||||||
		Loading…
	
		Reference in New Issue
	
	Block a user
	 bunnei
						bunnei