citra-emu
/
citra
Archived
1
0
Fork 0

OpenGL Cache: Ignore format reinterpretation hack

Several games such as Smash will cause some regions that are cached on
the gpu to be revalidated, but (seemingly) we can just ignore these
cases. If the data is already found on the gpu in dirty_regions, then we
validate those, and skip flushing that region from cpu.

Its unknown if this breaks any games, but it does speed up many games.
Additionally, it removes outlines in the pokemon games.
This commit is contained in:
James Rowe 2017-11-29 21:09:03 -07:00
parent 5b872c41d8
commit 0498d34d18
1 changed files with 21 additions and 4 deletions

View File

@ -1269,11 +1269,15 @@ void RasterizerCacheOpenGL::ValidateSurface(const Surface& surface, PAddr addr,
return; return;
} }
const auto validate_regions = surface->invalid_regions.find(validate_interval); auto validate_regions = surface->invalid_regions & validate_interval;
auto notify_validated = [&](SurfaceInterval interval) {
surface->invalid_regions.erase(interval);
validate_regions.erase(interval);
};
for (;;) { for (;;) {
const auto it = validate_regions.begin(); const auto it = validate_regions.begin();
if (it == surface->invalid_regions.end()) if (it == validate_regions.end())
break; break;
const auto interval = *it & validate_interval; const auto interval = *it & validate_interval;
@ -1285,15 +1289,28 @@ void RasterizerCacheOpenGL::ValidateSurface(const Surface& surface, PAddr addr,
if (copy_surface != nullptr) { if (copy_surface != nullptr) {
SurfaceInterval copy_interval = params.GetCopyableInterval(copy_surface); SurfaceInterval copy_interval = params.GetCopyableInterval(copy_surface);
CopySurface(copy_surface, surface, copy_interval); CopySurface(copy_surface, surface, copy_interval);
validate_regions.erase(interval); notify_validated(copy_interval);
continue; continue;
} }
// HACK HACK HACK: Ignore format reinterpretation
// this is a placeholder for HW texture decoding/encoding
constexpr bool IGNORE_FORMAT_REINTERPRETING = true;
bool retry = false;
if (IGNORE_FORMAT_REINTERPRETING) {
for (const auto& pair : RangeFromInterval(dirty_regions, interval)) {
validate_regions.erase(pair.first & interval);
retry = true;
}
}
if (retry)
continue;
// Load data from 3DS memory // Load data from 3DS memory
FlushRegion(params.addr, params.size); FlushRegion(params.addr, params.size);
surface->LoadGLBuffer(params.addr, params.end); surface->LoadGLBuffer(params.addr, params.end);
surface->UploadGLTexture(surface->GetSubRect(params)); surface->UploadGLTexture(surface->GetSubRect(params));
validate_regions.erase(interval) notify_validated(params.GetInterval());
} }
} }