rsx: Driver compatibility improvements (#9131)

* rsx: Refactor vertex clip emit to avoid using f64 unnecessarily

- Fixes driver crash on intel

* vk: Add NVIDIA driver version check

- Warn if user has outdated drivers with known problems
This commit is contained in:
kd-11 2020-10-27 13:22:15 +03:00 committed by GitHub
parent 8ce0eaa9d0
commit b32eecb5a7
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 52 additions and 35 deletions

View File

@ -583,21 +583,42 @@ namespace glsl
if (props.domain == glsl::program_domain::glsl_vertex_program && props.emulate_zclip_transform)
{
OS <<
"double rcp_precise(double x)\n"
"{\n"
" double scaled = x * 0.0009765625;\n"
" double inv = 1.0 / scaled;\n"
" return inv * 0.0009765625;\n"
"}\n"
"\n"
"vec4 apply_zclip_xform(const in vec4 pos, const in float near_plane, const in float far_plane)\n"
"{\n";
if (!props.emulate_depth_clip_only)
if (props.emulate_depth_clip_only)
{
// Declare rcp_precise. Requires f64 support in the drivers.
// This is required to handle precision drift during division for extended depth range.
OS <<
"double rcp_precise(double x)\n"
"{\n"
" double scaled = x * 0.0009765625;\n"
" double inv = 1.0 / scaled;\n"
" return inv * 0.0009765625;\n"
"}\n"
"\n"
// Technically the depth value here is the 'final' depth that should be stored in the Z buffer.
// Forward mapping eqn is d' = d * (f - n) + n, where d' is the stored Z value (this) and d is the normalized API value.
"vec4 apply_zclip_xform(const in vec4 pos, const in float near_plane, const in float far_plane)\n"
"{\n"
" if (far_plane != 0.0)\n"
" {\n"
" double z_range = (far_plane > near_plane)? (far_plane - near_plane) : far_plane;\n"
" double inv_range = rcp_precise(z_range);\n"
" float d = float(pos.z * rcp_precise(pos.w));\n"
" float new_d = (d - near_plane) * float(inv_range);\n"
" return vec4(pos.x, pos.y, (new_d * pos.w), pos.w);\n"
" }\n"
" else\n"
" {\n"
" return pos;\n" // Only values where Z=0 can ever pass this clip
" }\n"
"}\n\n";
}
else
{
OS <<
" float d = float(pos.z * rcp_precise(pos.w));\n"
"vec4 apply_zclip_xform(const in vec4 pos, const in float near_plane, const in float far_plane)\n"
"{\n"
" float d = float(pos.z / pos.w);\n"
" if (d < 0.f && d >= near_plane)\n"
" {\n"
" // Clamp\n"
@ -613,29 +634,9 @@ namespace glsl
" return pos;\n"
" }\n"
"\n"
" return vec4(pos.x, pos.y, d * pos.w, pos.w);\n";
" return vec4(pos.x, pos.y, d * pos.w, pos.w);\n"
"}\n\n";
}
else
{
// Technically the depth value here is the 'final' depth that should be stored in the Z buffer.
// Forward mapping eqn is d' = d * (f - n) + n, where d' is the stored Z value (this) and d is the normalized API value.
OS <<
" if (far_plane != 0.0)\n"
" {\n"
" double z_range = (far_plane > near_plane)? (far_plane - near_plane) : far_plane;\n"
" double inv_range = rcp_precise(z_range);\n"
" float d = float(pos.z * rcp_precise(pos.w));\n"
" float new_d = (d - near_plane) * float(inv_range);\n"
" return vec4(pos.x, pos.y, (new_d * pos.w), pos.w);\n"
" }\n"
" else\n"
" {\n"
" return pos;\n" // Only values where Z=0 can ever pass this clip
" }\n";
}
OS <<
"}\n\n";
return;
}

View File

@ -715,6 +715,22 @@ private:
// See https://bugs.freedesktop.org/show_bug.cgi?id=110970
rsx_log.fatal("RADV drivers have a major driver bug with LLVM 8.0.0 resulting in no visual output. Upgrade to LLVM version 8.0.1 or greater to avoid this issue.");
}
else if (get_driver_vendor() == driver_vendor::NVIDIA)
{
#ifdef _WIN32
// SPIRV bugs were fixed in 452.28 for windows
const u32 threshold_version = (452u >> 22) | (28 >> 14);
#else
// SPIRV bugs were fixed in 450.56 for linux/BSD
const u32 threshold_version = (450u >> 22) | (56 >> 14);
#endif
const auto current_version = props.driverVersion & ~0x3fffu; // Clear patch and revision fields
if (current_version < threshold_version)
{
rsx_log.error("Your current NVIDIA graphics driver version %s has known issues and is unsupported. Update to the latest NVIDIA driver.",
get_driver_version());
}
}
if (get_chip_class() == chip_class::AMD_vega)
{