diff options
| author | JMC47 <JMC4789@gmail.com> | 2022-04-24 13:30:04 -0400 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2022-04-24 13:30:04 -0400 |
| commit | c42392c565be2915af17588e2215c4b2861aeb53 (patch) | |
| tree | ac554936562a3c49e0be5a1d17e070243baf0fcf /Source/Core/VideoCommon/PixelShaderGen.cpp | |
| parent | 61edcf7e4fd2cef2ad95022abb2e5fc46f7433ed (diff) | |
| parent | 259a5fc7c02d48f21d2479d8e259519bc4ed443e (diff) | |
Merge pull request #10290 from OatmealDome/m1-earlyz-bug
DriverDetails: Add broken discard with early-Z bug on Apple Silicon GPUs
Diffstat (limited to 'Source/Core/VideoCommon/PixelShaderGen.cpp')
| -rw-r--r-- | Source/Core/VideoCommon/PixelShaderGen.cpp | 51 |
1 files changed, 37 insertions, 14 deletions
diff --git a/Source/Core/VideoCommon/PixelShaderGen.cpp b/Source/Core/VideoCommon/PixelShaderGen.cpp index 82de68a290..4a9e9105a8 100644 --- a/Source/Core/VideoCommon/PixelShaderGen.cpp +++ b/Source/Core/VideoCommon/PixelShaderGen.cpp @@ -321,7 +321,9 @@ PixelShaderUid GetPixelShaderUid() BlendingState state = {}; state.Generate(bpmem); - if (state.usedualsrc && state.dstalpha && g_ActiveConfig.backend_info.bSupportsFramebufferFetch && + if (((state.usedualsrc && state.dstalpha) || + DriverDetails::HasBug(DriverDetails::BUG_BROKEN_DISCARD_WITH_EARLY_Z)) && + g_ActiveConfig.backend_info.bSupportsFramebufferFetch && !g_ActiveConfig.backend_info.bSupportsDualSourceBlend) { uid_data->blend_enable = state.blendenable; @@ -944,10 +946,15 @@ ShaderCode GeneratePixelShaderCode(APIType api_type, const ShaderHostConfig& hos (!DriverDetails::HasBug(DriverDetails::BUG_BROKEN_DUAL_SOURCE_BLENDING) || uid_data->useDstAlpha); const bool use_shader_blend = - !use_dual_source && uid_data->useDstAlpha && host_config.backend_shader_framebuffer_fetch; + !use_dual_source && + (uid_data->useDstAlpha || + DriverDetails::HasBug(DriverDetails::BUG_BROKEN_DISCARD_WITH_EARLY_Z)) && + host_config.backend_shader_framebuffer_fetch; const bool use_shader_logic_op = !host_config.backend_logic_op && uid_data->logic_op_enable && host_config.backend_shader_framebuffer_fetch; - const bool use_framebuffer_fetch = use_shader_blend || use_shader_logic_op; + const bool use_framebuffer_fetch = + use_shader_blend || use_shader_logic_op || + DriverDetails::HasBug(DriverDetails::BUG_BROKEN_DISCARD_WITH_EARLY_Z); if (api_type == APIType::OpenGL || api_type == APIType::Vulkan) { @@ -1869,9 +1876,23 @@ static void WriteAlphaTest(ShaderCode& out, const pixel_shader_uid_data* uid_dat // ZCOMPLOC HACK: if (!uid_data->alpha_test_use_zcomploc_hack) { - out.Write("\t\tdiscard;\n"); - if (api_type == APIType::D3D) +#ifdef __APPLE__ + if (uid_data->forced_early_z && + DriverDetails::HasBug(DriverDetails::BUG_BROKEN_DISCARD_WITH_EARLY_Z)) + { + // Instead of using discard, fetch the framebuffer's color value and use it as the output + // for this fragment. + out.Write("\t\t{} = float4(initial_ocol0.xyz, 1.0);\n", + use_dual_source ? "real_ocol0" : "ocol0"); out.Write("\t\treturn;\n"); + } + else +#endif + { + out.Write("\t\tdiscard;\n"); + if (api_type == APIType::D3D) + out.Write("\t\treturn;\n"); + } } out.Write("\t}}\n"); @@ -2018,8 +2039,8 @@ static void WriteBlend(ShaderCode& out, const pixel_shader_uid_data* uid_data) "float3(1,1,1);", // ONE "initial_ocol0.rgb;", // DSTCLR "float3(1,1,1) - initial_ocol0.rgb;", // INVDSTCLR - "ocol1.aaa;", // SRCALPHA - "float3(1,1,1) - ocol1.aaa;", // INVSRCALPHA + "src_color.aaa;", // SRCALPHA + "float3(1,1,1) - src_color.aaa;", // INVSRCALPHA "initial_ocol0.aaa;", // DSTALPHA "float3(1,1,1) - initial_ocol0.aaa;", // INVDSTALPHA }; @@ -2028,8 +2049,8 @@ static void WriteBlend(ShaderCode& out, const pixel_shader_uid_data* uid_data) "1.0;", // ONE "initial_ocol0.a;", // DSTCLR "1.0 - initial_ocol0.a;", // INVDSTCLR - "ocol1.a;", // SRCALPHA - "1.0 - ocol1.a;", // INVSRCALPHA + "src_color.a;", // SRCALPHA + "1.0 - src_color.a;", // INVSRCALPHA "initial_ocol0.a;", // DSTALPHA "1.0 - initial_ocol0.a;", // INVDSTALPHA }; @@ -2038,8 +2059,8 @@ static void WriteBlend(ShaderCode& out, const pixel_shader_uid_data* uid_data) "float3(1,1,1);", // ONE "ocol0.rgb;", // SRCCLR "float3(1,1,1) - ocol0.rgb;", // INVSRCCLR - "ocol1.aaa;", // SRCALHA - "float3(1,1,1) - ocol1.aaa;", // INVSRCALPHA + "src_color.aaa;", // SRCALHA + "float3(1,1,1) - src_color.aaa;", // INVSRCALPHA "initial_ocol0.aaa;", // DSTALPHA "float3(1,1,1) - initial_ocol0.aaa;", // INVDSTALPHA }; @@ -2048,12 +2069,14 @@ static void WriteBlend(ShaderCode& out, const pixel_shader_uid_data* uid_data) "1.0;", // ONE "ocol0.a;", // SRCCLR "1.0 - ocol0.a;", // INVSRCCLR - "ocol1.a;", // SRCALPHA - "1.0 - ocol1.a;", // INVSRCALPHA + "src_color.a;", // SRCALPHA + "1.0 - src_color.a;", // INVSRCALPHA "initial_ocol0.a;", // DSTALPHA "1.0 - initial_ocol0.a;", // INVDSTALPHA }; - out.Write("\tfloat4 blend_src;\n"); + out.Write("\tfloat4 src_color = {};\n" + "\tfloat4 blend_src;", + uid_data->useDstAlpha ? "ocol1" : "ocol0"); out.Write("\tblend_src.rgb = {}\n", blend_src_factor[uid_data->blend_src_factor]); out.Write("\tblend_src.a = {}\n", blend_src_factor_alpha[uid_data->blend_src_factor_alpha]); out.Write("\tfloat4 blend_dst;\n"); |
