summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorGravatar bunnei2018-10-12 22:24:40 -0400
committerGravatar bunnei2018-10-16 11:31:00 -0400
commit4e9683e9d5518a2e5dc69ddd12f20685a94646e2 (patch)
tree41bb16430adb994f0dd5ff2742830a7132b4accc /src
parentmemory_manager: Add a method for querying the end of a mapped GPU region. (diff)
downloadyuzu-4e9683e9d5518a2e5dc69ddd12f20685a94646e2.tar.gz
yuzu-4e9683e9d5518a2e5dc69ddd12f20685a94646e2.tar.xz
yuzu-4e9683e9d5518a2e5dc69ddd12f20685a94646e2.zip
gl_rasterizer_cache: Clamp cached surface size to mapped GPU region size.
Diffstat (limited to 'src')
-rw-r--r--src/video_core/renderer_opengl/gl_rasterizer_cache.cpp45
-rw-r--r--src/video_core/renderer_opengl/gl_rasterizer_cache.h11
2 files changed, 37 insertions, 19 deletions
diff --git a/src/video_core/renderer_opengl/gl_rasterizer_cache.cpp b/src/video_core/renderer_opengl/gl_rasterizer_cache.cpp
index 1bb842fe7..24781a3c1 100644
--- a/src/video_core/renderer_opengl/gl_rasterizer_cache.cpp
+++ b/src/video_core/renderer_opengl/gl_rasterizer_cache.cpp
@@ -34,16 +34,29 @@ struct FormatTuple {
34 bool compressed; 34 bool compressed;
35}; 35};
36 36
37static VAddr TryGetCpuAddr(Tegra::GPUVAddr gpu_addr) { 37void SurfaceParams::InitCacheParameters(Tegra::GPUVAddr gpu_addr) {
38 auto& gpu{Core::System::GetInstance().GPU()}; 38 auto& memory_manager{Core::System::GetInstance().GPU().MemoryManager()};
39 const auto cpu_addr{gpu.MemoryManager().GpuToCpuAddress(gpu_addr)}; 39 const auto cpu_addr{memory_manager.GpuToCpuAddress(gpu_addr)};
40 return cpu_addr ? *cpu_addr : 0; 40 const auto max_size{memory_manager.GetRegionEnd(gpu_addr) - gpu_addr};
41
42 addr = cpu_addr ? *cpu_addr : 0;
43 size_in_bytes_total = SizeInBytesTotal();
44 size_in_bytes_2d = SizeInBytes2D();
45
46 // Clamp sizes to mapped GPU memory region
47 if (size_in_bytes_2d > max_size) {
48 LOG_ERROR(HW_GPU, "Surface size {} exceeds region size {}", size_in_bytes_2d, max_size);
49 size_in_bytes_total = max_size;
50 size_in_bytes_2d = max_size;
51 } else if (size_in_bytes_total > max_size) {
52 LOG_ERROR(HW_GPU, "Surface size {} exceeds region size {}", size_in_bytes_total, max_size);
53 size_in_bytes_total = max_size;
54 }
41} 55}
42 56
43/*static*/ SurfaceParams SurfaceParams::CreateForTexture( 57/*static*/ SurfaceParams SurfaceParams::CreateForTexture(
44 const Tegra::Texture::FullTextureInfo& config, const GLShader::SamplerEntry& entry) { 58 const Tegra::Texture::FullTextureInfo& config, const GLShader::SamplerEntry& entry) {
45 SurfaceParams params{}; 59 SurfaceParams params{};
46 params.addr = TryGetCpuAddr(config.tic.Address());
47 params.is_tiled = config.tic.IsTiled(); 60 params.is_tiled = config.tic.IsTiled();
48 params.block_width = params.is_tiled ? config.tic.BlockWidth() : 0, 61 params.block_width = params.is_tiled ? config.tic.BlockWidth() : 0,
49 params.block_height = params.is_tiled ? config.tic.BlockHeight() : 0, 62 params.block_height = params.is_tiled ? config.tic.BlockHeight() : 0,
@@ -87,18 +100,18 @@ static VAddr TryGetCpuAddr(Tegra::GPUVAddr gpu_addr) {
87 break; 100 break;
88 } 101 }
89 102
90 params.size_in_bytes_total = params.SizeInBytesTotal();
91 params.size_in_bytes_2d = params.SizeInBytes2D();
92 params.max_mip_level = config.tic.max_mip_level + 1; 103 params.max_mip_level = config.tic.max_mip_level + 1;
93 params.rt = {}; 104 params.rt = {};
94 105
106 params.InitCacheParameters(config.tic.Address());
107
95 return params; 108 return params;
96} 109}
97 110
98/*static*/ SurfaceParams SurfaceParams::CreateForFramebuffer(std::size_t index) { 111/*static*/ SurfaceParams SurfaceParams::CreateForFramebuffer(std::size_t index) {
99 const auto& config{Core::System::GetInstance().GPU().Maxwell3D().regs.rt[index]}; 112 const auto& config{Core::System::GetInstance().GPU().Maxwell3D().regs.rt[index]};
100 SurfaceParams params{}; 113 SurfaceParams params{};
101 params.addr = TryGetCpuAddr(config.Address()); 114
102 params.is_tiled = 115 params.is_tiled =
103 config.memory_layout.type == Tegra::Engines::Maxwell3D::Regs::InvMemoryLayout::BlockLinear; 116 config.memory_layout.type == Tegra::Engines::Maxwell3D::Regs::InvMemoryLayout::BlockLinear;
104 params.block_width = 1 << config.memory_layout.block_width; 117 params.block_width = 1 << config.memory_layout.block_width;
@@ -112,8 +125,6 @@ static VAddr TryGetCpuAddr(Tegra::GPUVAddr gpu_addr) {
112 params.unaligned_height = config.height; 125 params.unaligned_height = config.height;
113 params.target = SurfaceTarget::Texture2D; 126 params.target = SurfaceTarget::Texture2D;
114 params.depth = 1; 127 params.depth = 1;
115 params.size_in_bytes_total = params.SizeInBytesTotal();
116 params.size_in_bytes_2d = params.SizeInBytes2D();
117 params.max_mip_level = 0; 128 params.max_mip_level = 0;
118 129
119 // Render target specific parameters, not used for caching 130 // Render target specific parameters, not used for caching
@@ -122,6 +133,8 @@ static VAddr TryGetCpuAddr(Tegra::GPUVAddr gpu_addr) {
122 params.rt.layer_stride = config.layer_stride; 133 params.rt.layer_stride = config.layer_stride;
123 params.rt.base_layer = config.base_layer; 134 params.rt.base_layer = config.base_layer;
124 135
136 params.InitCacheParameters(config.Address());
137
125 return params; 138 return params;
126} 139}
127 140
@@ -130,7 +143,7 @@ static VAddr TryGetCpuAddr(Tegra::GPUVAddr gpu_addr) {
130 u32 block_width, u32 block_height, u32 block_depth, 143 u32 block_width, u32 block_height, u32 block_depth,
131 Tegra::Engines::Maxwell3D::Regs::InvMemoryLayout type) { 144 Tegra::Engines::Maxwell3D::Regs::InvMemoryLayout type) {
132 SurfaceParams params{}; 145 SurfaceParams params{};
133 params.addr = TryGetCpuAddr(zeta_address); 146
134 params.is_tiled = type == Tegra::Engines::Maxwell3D::Regs::InvMemoryLayout::BlockLinear; 147 params.is_tiled = type == Tegra::Engines::Maxwell3D::Regs::InvMemoryLayout::BlockLinear;
135 params.block_width = 1 << std::min(block_width, 5U); 148 params.block_width = 1 << std::min(block_width, 5U);
136 params.block_height = 1 << std::min(block_height, 5U); 149 params.block_height = 1 << std::min(block_height, 5U);
@@ -143,18 +156,18 @@ static VAddr TryGetCpuAddr(Tegra::GPUVAddr gpu_addr) {
143 params.unaligned_height = zeta_height; 156 params.unaligned_height = zeta_height;
144 params.target = SurfaceTarget::Texture2D; 157 params.target = SurfaceTarget::Texture2D;
145 params.depth = 1; 158 params.depth = 1;
146 params.size_in_bytes_total = params.SizeInBytesTotal();
147 params.size_in_bytes_2d = params.SizeInBytes2D();
148 params.max_mip_level = 0; 159 params.max_mip_level = 0;
149 params.rt = {}; 160 params.rt = {};
150 161
162 params.InitCacheParameters(zeta_address);
163
151 return params; 164 return params;
152} 165}
153 166
154/*static*/ SurfaceParams SurfaceParams::CreateForFermiCopySurface( 167/*static*/ SurfaceParams SurfaceParams::CreateForFermiCopySurface(
155 const Tegra::Engines::Fermi2D::Regs::Surface& config) { 168 const Tegra::Engines::Fermi2D::Regs::Surface& config) {
156 SurfaceParams params{}; 169 SurfaceParams params{};
157 params.addr = TryGetCpuAddr(config.Address()); 170
158 params.is_tiled = !config.linear; 171 params.is_tiled = !config.linear;
159 params.block_width = params.is_tiled ? std::min(config.BlockWidth(), 32U) : 0, 172 params.block_width = params.is_tiled ? std::min(config.BlockWidth(), 32U) : 0,
160 params.block_height = params.is_tiled ? std::min(config.BlockHeight(), 32U) : 0, 173 params.block_height = params.is_tiled ? std::min(config.BlockHeight(), 32U) : 0,
@@ -167,11 +180,11 @@ static VAddr TryGetCpuAddr(Tegra::GPUVAddr gpu_addr) {
167 params.unaligned_height = config.height; 180 params.unaligned_height = config.height;
168 params.target = SurfaceTarget::Texture2D; 181 params.target = SurfaceTarget::Texture2D;
169 params.depth = 1; 182 params.depth = 1;
170 params.size_in_bytes_total = params.SizeInBytesTotal();
171 params.size_in_bytes_2d = params.SizeInBytes2D();
172 params.max_mip_level = 0; 183 params.max_mip_level = 0;
173 params.rt = {}; 184 params.rt = {};
174 185
186 params.InitCacheParameters(config.Address());
187
175 return params; 188 return params;
176} 189}
177 190
diff --git a/src/video_core/renderer_opengl/gl_rasterizer_cache.h b/src/video_core/renderer_opengl/gl_rasterizer_cache.h
index a15fb7b07..f6f7aad82 100644
--- a/src/video_core/renderer_opengl/gl_rasterizer_cache.h
+++ b/src/video_core/renderer_opengl/gl_rasterizer_cache.h
@@ -742,7 +742,9 @@ struct SurfaceParams {
742 other.depth); 742 other.depth);
743 } 743 }
744 744
745 VAddr addr; 745 /// Initializes parameters for caching, should be called after everything has been initialized
746 void InitCacheParameters(Tegra::GPUVAddr gpu_addr);
747
746 bool is_tiled; 748 bool is_tiled;
747 u32 block_width; 749 u32 block_width;
748 u32 block_height; 750 u32 block_height;
@@ -754,11 +756,14 @@ struct SurfaceParams {
754 u32 height; 756 u32 height;
755 u32 depth; 757 u32 depth;
756 u32 unaligned_height; 758 u32 unaligned_height;
757 std::size_t size_in_bytes_total;
758 std::size_t size_in_bytes_2d;
759 SurfaceTarget target; 759 SurfaceTarget target;
760 u32 max_mip_level; 760 u32 max_mip_level;
761 761
762 // Parameters used for caching
763 VAddr addr;
764 std::size_t size_in_bytes_total;
765 std::size_t size_in_bytes_2d;
766
762 // Render target specific parameters, not used in caching 767 // Render target specific parameters, not used in caching
763 struct { 768 struct {
764 u32 index; 769 u32 index;