From bd6d22973381b43369670300a707e86084c040e0 Mon Sep 17 00:00:00 2001 From: Jules Blok Date: Tue, 16 Dec 2014 17:28:35 +0100 Subject: [PATCH] GeometryShader: Disable the geometry shader stage if it is a pass-through shader. --- Source/Core/VideoBackends/D3D/GeometryShaderCache.cpp | 11 ++++++++++- Source/Core/VideoBackends/D3D/GeometryShaderCache.h | 1 + Source/Core/VideoBackends/OGL/ProgramShaderCache.cpp | 3 ++- Source/Core/VideoCommon/GeometryShaderGen.cpp | 6 ++++++ Source/Core/VideoCommon/GeometryShaderGen.h | 1 + 5 files changed, 20 insertions(+), 2 deletions(-) diff --git a/Source/Core/VideoBackends/D3D/GeometryShaderCache.cpp b/Source/Core/VideoBackends/D3D/GeometryShaderCache.cpp index bed0ff95b7..7088cd70f5 100644 --- a/Source/Core/VideoBackends/D3D/GeometryShaderCache.cpp +++ b/Source/Core/VideoBackends/D3D/GeometryShaderCache.cpp @@ -28,6 +28,7 @@ GeometryShaderCache::GSCache GeometryShaderCache::GeometryShaders; const GeometryShaderCache::GSCacheEntry* GeometryShaderCache::last_entry; GeometryShaderUid GeometryShaderCache::last_uid; UidChecker GeometryShaderCache::geometry_uid_checker; +const GeometryShaderCache::GSCacheEntry GeometryShaderCache::pass_entry; ID3D11GeometryShader* ClearGeometryShader = nullptr; ID3D11GeometryShader* CopyGeometryShader = nullptr; @@ -203,12 +204,20 @@ bool GeometryShaderCache::SetShader(u32 primitive_type) if (uid == last_uid) { GFX_DEBUGGER_PAUSE_AT(NEXT_PIXEL_SHADER_CHANGE,true); - return (last_entry->shader != nullptr); + return true; } } last_uid = uid; + // Check if the shader is a pass-through shader + if (IsPassthroughGeometryShader(uid)) + { + // Return the default pass-through shader + last_entry = &pass_entry; + return true; + } + // Check if the shader is already in the cache GSCache::iterator iter; iter = GeometryShaders.find(uid); diff --git a/Source/Core/VideoBackends/D3D/GeometryShaderCache.h b/Source/Core/VideoBackends/D3D/GeometryShaderCache.h index fe4aea4a36..d88b88f4ae 100644 --- a/Source/Core/VideoBackends/D3D/GeometryShaderCache.h +++ b/Source/Core/VideoBackends/D3D/GeometryShaderCache.h @@ -43,6 +43,7 @@ private: static GSCache GeometryShaders; static const GSCacheEntry* last_entry; static GeometryShaderUid last_uid; + static const GSCacheEntry pass_entry; static UidChecker geometry_uid_checker; }; diff --git a/Source/Core/VideoBackends/OGL/ProgramShaderCache.cpp b/Source/Core/VideoBackends/OGL/ProgramShaderCache.cpp index d2ec0d049b..8f90aff28a 100644 --- a/Source/Core/VideoBackends/OGL/ProgramShaderCache.cpp +++ b/Source/Core/VideoBackends/OGL/ProgramShaderCache.cpp @@ -211,7 +211,8 @@ SHADER* ProgramShaderCache::SetShader(DSTALPHA_MODE dstAlphaMode, u32 components ShaderCode gcode; GenerateVertexShaderCode(vcode, components, API_OPENGL); GeneratePixelShaderCode(pcode, dstAlphaMode, API_OPENGL, components); - GenerateGeometryShaderCode(gcode, primitive_type, API_OPENGL); + if (!IsPassthroughGeometryShader(uid.guid)) + GenerateGeometryShaderCode(gcode, primitive_type, API_OPENGL); if (g_ActiveConfig.bEnableShaderDebugging) { diff --git a/Source/Core/VideoCommon/GeometryShaderGen.cpp b/Source/Core/VideoCommon/GeometryShaderGen.cpp index bf40056a8d..3d478a6a4d 100644 --- a/Source/Core/VideoCommon/GeometryShaderGen.cpp +++ b/Source/Core/VideoCommon/GeometryShaderGen.cpp @@ -281,3 +281,9 @@ void GenerateGeometryShaderCode(ShaderCode& object, u32 primitive_type, API_TYPE { GenerateGeometryShader(object, primitive_type, ApiType); } + +bool IsPassthroughGeometryShader(GeometryShaderUid& object) +{ + geometry_shader_uid_data* uid_data = object.GetUidData(); + return uid_data->primitive_type == PRIMITIVE_TRIANGLES && !uid_data->stereo; +} diff --git a/Source/Core/VideoCommon/GeometryShaderGen.h b/Source/Core/VideoCommon/GeometryShaderGen.h index 93e222b25e..0f66f7a4f9 100644 --- a/Source/Core/VideoCommon/GeometryShaderGen.h +++ b/Source/Core/VideoCommon/GeometryShaderGen.h @@ -25,3 +25,4 @@ typedef ShaderUid GeometryShaderUid; void GenerateGeometryShaderCode(ShaderCode& object, u32 primitive_type, API_TYPE ApiType); void GetGeometryShaderUid(GeometryShaderUid& object, u32 primitive_type, API_TYPE ApiType); +bool IsPassthroughGeometryShader(GeometryShaderUid& object);