aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorgdkchan <gab.dark.100@gmail.com>2023-04-24 03:34:38 -0300
committerGitHub <noreply@github.com>2023-04-24 08:34:38 +0200
commit4dd77316f722f6b429063784b56ddced7883ea1d (patch)
treec2dcb3142e8fd35367d313318b2467e46b284b5c
parent3f98369a17a313c32e1a00cb9b81c6695ac76f27 (diff)
Use vector transform feedback outputs with fragment shaders (#4708)1.1.730
* Use vector transform feedback outputs with fragment shaders * Shader cache version bump * Fix missing outputs when vector transform feedback outputs are used
-rw-r--r--Ryujinx.Graphics.Gpu/Shader/DiskCache/DiskCacheHostStorage.cs2
-rw-r--r--Ryujinx.Graphics.Gpu/Shader/ShaderCache.cs2
-rw-r--r--Ryujinx.Graphics.Shader/CodeGen/Glsl/Declarations.cs42
-rw-r--r--Ryujinx.Graphics.Shader/CodeGen/Glsl/OperandManager.cs2
-rw-r--r--Ryujinx.Graphics.Shader/CodeGen/Spirv/CodeGenContext.cs2
-rw-r--r--Ryujinx.Graphics.Shader/CodeGen/Spirv/Declarations.cs2
-rw-r--r--Ryujinx.Graphics.Shader/StructuredIr/StructuredProgram.cs2
-rw-r--r--Ryujinx.Graphics.Shader/Translation/ShaderConfig.cs11
-rw-r--r--Ryujinx.Graphics.Shader/Translation/TranslatorContext.cs4
9 files changed, 37 insertions, 32 deletions
diff --git a/Ryujinx.Graphics.Gpu/Shader/DiskCache/DiskCacheHostStorage.cs b/Ryujinx.Graphics.Gpu/Shader/DiskCache/DiskCacheHostStorage.cs
index 48464f83..cad2341b 100644
--- a/Ryujinx.Graphics.Gpu/Shader/DiskCache/DiskCacheHostStorage.cs
+++ b/Ryujinx.Graphics.Gpu/Shader/DiskCache/DiskCacheHostStorage.cs
@@ -22,7 +22,7 @@ namespace Ryujinx.Graphics.Gpu.Shader.DiskCache
private const ushort FileFormatVersionMajor = 1;
private const ushort FileFormatVersionMinor = 2;
private const uint FileFormatVersionPacked = ((uint)FileFormatVersionMajor << 16) | FileFormatVersionMinor;
- private const uint CodeGenVersion = 4703;
+ private const uint CodeGenVersion = 4707;
private const string SharedTocFileName = "shared.toc";
private const string SharedDataFileName = "shared.data";
diff --git a/Ryujinx.Graphics.Gpu/Shader/ShaderCache.cs b/Ryujinx.Graphics.Gpu/Shader/ShaderCache.cs
index 11f7085d..e1ab9327 100644
--- a/Ryujinx.Graphics.Gpu/Shader/ShaderCache.cs
+++ b/Ryujinx.Graphics.Gpu/Shader/ShaderCache.cs
@@ -449,7 +449,7 @@ namespace Ryujinx.Graphics.Gpu.Shader
if (translatorContexts[i] != null)
{
translatorContexts[i].SetGeometryShaderLayerInputAttribute(info.GpLayerInputAttribute);
- translatorContexts[i].SetLastInVertexPipeline(translatorContexts[5] != null);
+ translatorContexts[i].SetLastInVertexPipeline();
break;
}
}
diff --git a/Ryujinx.Graphics.Shader/CodeGen/Glsl/Declarations.cs b/Ryujinx.Graphics.Shader/CodeGen/Glsl/Declarations.cs
index 9032ca59..5e53d62a 100644
--- a/Ryujinx.Graphics.Shader/CodeGen/Glsl/Declarations.cs
+++ b/Ryujinx.Graphics.Shader/CodeGen/Glsl/Declarations.cs
@@ -569,7 +569,23 @@ namespace Ryujinx.Graphics.Shader.CodeGen.Glsl
if (context.Config.TransformFeedbackEnabled && context.Config.Stage == ShaderStage.Fragment)
{
- for (int c = 0; c < 4; c++)
+ int attrOffset = AttributeConsts.UserAttributeBase + attr * 16;
+ int components = context.Info.GetTransformFeedbackOutputComponents(attrOffset);
+
+ if (components > 1)
+ {
+ string type = components switch
+ {
+ 2 => "vec2",
+ 3 => "vec3",
+ 4 => "vec4",
+ _ => "float"
+ };
+
+ context.AppendLine($"layout (location = {attr}) in {type} {name};");
+ }
+
+ for (int c = components > 1 ? components : 0; c < 4; c++)
{
char swzMask = "xyzw"[c];
@@ -642,7 +658,7 @@ namespace Ryujinx.Graphics.Shader.CodeGen.Glsl
if (context.Config.TransformFeedbackEnabled && context.Config.LastInVertexPipeline)
{
int attrOffset = AttributeConsts.UserAttributeBase + attr * 16;
- int components = context.Config.LastInPipeline ? context.Info.GetTransformFeedbackOutputComponents(attrOffset) : 1;
+ int components = context.Info.GetTransformFeedbackOutputComponents(attrOffset);
if (components > 1)
{
@@ -664,22 +680,20 @@ namespace Ryujinx.Graphics.Shader.CodeGen.Glsl
context.AppendLine($"layout (location = {attr}{xfb}) out {type} {name};");
}
- else
- {
- for (int c = 0; c < 4; c++)
- {
- char swzMask = "xyzw"[c];
- string xfb = string.Empty;
+ for (int c = components > 1 ? components : 0; c < 4; c++)
+ {
+ char swzMask = "xyzw"[c];
- var tfOutput = context.Info.GetTransformFeedbackOutput(attrOffset + c * 4);
- if (tfOutput.Valid)
- {
- xfb = $", xfb_buffer = {tfOutput.Buffer}, xfb_offset = {tfOutput.Offset}, xfb_stride = {tfOutput.Stride}";
- }
+ string xfb = string.Empty;
- context.AppendLine($"layout (location = {attr}, component = {c}{xfb}) out float {name}_{swzMask};");
+ var tfOutput = context.Info.GetTransformFeedbackOutput(attrOffset + c * 4);
+ if (tfOutput.Valid)
+ {
+ xfb = $", xfb_buffer = {tfOutput.Buffer}, xfb_offset = {tfOutput.Offset}, xfb_stride = {tfOutput.Stride}";
}
+
+ context.AppendLine($"layout (location = {attr}, component = {c}{xfb}) out float {name}_{swzMask};");
}
}
else
diff --git a/Ryujinx.Graphics.Shader/CodeGen/Glsl/OperandManager.cs b/Ryujinx.Graphics.Shader/CodeGen/Glsl/OperandManager.cs
index ce1ab50e..ec761fa6 100644
--- a/Ryujinx.Graphics.Shader/CodeGen/Glsl/OperandManager.cs
+++ b/Ryujinx.Graphics.Shader/CodeGen/Glsl/OperandManager.cs
@@ -220,7 +220,7 @@ namespace Ryujinx.Graphics.Shader.CodeGen.Glsl
((config.LastInVertexPipeline && isOutAttr) ||
(config.Stage == ShaderStage.Fragment && !isOutAttr)))
{
- int components = config.LastInPipeline ? context.Info.GetTransformFeedbackOutputComponents(attrOffset) : 1;
+ int components = context.Info.GetTransformFeedbackOutputComponents(attrOffset);
string name = components > 1 ? $"{prefix}{(value >> 4)}" : $"{prefix}{(value >> 4)}_{swzMask}";
if (AttributeInfo.IsArrayAttributeGlsl(config.Stage, isOutAttr))
diff --git a/Ryujinx.Graphics.Shader/CodeGen/Spirv/CodeGenContext.cs b/Ryujinx.Graphics.Shader/CodeGen/Spirv/CodeGenContext.cs
index 41afdf18..e693307d 100644
--- a/Ryujinx.Graphics.Shader/CodeGen/Spirv/CodeGenContext.cs
+++ b/Ryujinx.Graphics.Shader/CodeGen/Spirv/CodeGenContext.cs
@@ -341,7 +341,7 @@ namespace Ryujinx.Graphics.Shader.CodeGen.Spirv
attrOffset = attr;
type = elemType;
- if (Config.LastInPipeline && isOutAttr)
+ if (isOutAttr)
{
int components = Info.GetTransformFeedbackOutputComponents(attr);
diff --git a/Ryujinx.Graphics.Shader/CodeGen/Spirv/Declarations.cs b/Ryujinx.Graphics.Shader/CodeGen/Spirv/Declarations.cs
index df42a13c..fdca5e89 100644
--- a/Ryujinx.Graphics.Shader/CodeGen/Spirv/Declarations.cs
+++ b/Ryujinx.Graphics.Shader/CodeGen/Spirv/Declarations.cs
@@ -673,7 +673,7 @@ namespace Ryujinx.Graphics.Shader.CodeGen.Spirv
int components = 1;
var type = attrInfo.Type & AggregateType.ElementTypeMask;
- if (context.Config.LastInPipeline && isOutAttr)
+ if (isOutAttr)
{
components = context.Info.GetTransformFeedbackOutputComponents(attr);
diff --git a/Ryujinx.Graphics.Shader/StructuredIr/StructuredProgram.cs b/Ryujinx.Graphics.Shader/StructuredIr/StructuredProgram.cs
index ec989cca..b8d38fa6 100644
--- a/Ryujinx.Graphics.Shader/StructuredIr/StructuredProgram.cs
+++ b/Ryujinx.Graphics.Shader/StructuredIr/StructuredProgram.cs
@@ -65,7 +65,7 @@ namespace Ryujinx.Graphics.Shader.StructuredIr
context.LeaveFunction();
}
- if (config.TransformFeedbackEnabled && config.LastInVertexPipeline)
+ if (config.TransformFeedbackEnabled && (config.LastInVertexPipeline || config.Stage == ShaderStage.Fragment))
{
for (int tfbIndex = 0; tfbIndex < 4; tfbIndex++)
{
diff --git a/Ryujinx.Graphics.Shader/Translation/ShaderConfig.cs b/Ryujinx.Graphics.Shader/Translation/ShaderConfig.cs
index 2caa8f63..15eb7ed1 100644
--- a/Ryujinx.Graphics.Shader/Translation/ShaderConfig.cs
+++ b/Ryujinx.Graphics.Shader/Translation/ShaderConfig.cs
@@ -17,7 +17,6 @@ namespace Ryujinx.Graphics.Shader.Translation
public ShaderStage Stage { get; }
public bool GpPassthrough { get; }
- public bool LastInPipeline { get; private set; }
public bool LastInVertexPipeline { get; private set; }
public bool HasLayerInputAttribute { get; private set; }
@@ -145,7 +144,6 @@ namespace Ryujinx.Graphics.Shader.Translation
OmapSampleMask = header.OmapSampleMask;
OmapDepth = header.OmapDepth;
TransformFeedbackEnabled = gpuAccessor.QueryTransformFeedbackEnabled();
- LastInPipeline = true;
LastInVertexPipeline = header.Stage < ShaderStage.Fragment;
}
@@ -253,13 +251,8 @@ namespace Ryujinx.Graphics.Shader.Translation
GpLayerInputAttribute = attr;
}
- public void SetLastInVertexPipeline(bool hasFragment)
+ public void SetLastInVertexPipeline()
{
- if (!hasFragment)
- {
- LastInPipeline = true;
- }
-
LastInVertexPipeline = true;
}
@@ -331,8 +324,6 @@ namespace Ryujinx.Graphics.Shader.Translation
config._perPatchAttributeLocations = locationsMap;
}
- LastInPipeline = false;
-
// We don't consider geometry shaders using the geometry shader passthrough feature
// as being the last because when this feature is used, it can't actually modify any of the outputs,
// so the stage that comes before it is the last one that can do modifications.
diff --git a/Ryujinx.Graphics.Shader/Translation/TranslatorContext.cs b/Ryujinx.Graphics.Shader/Translation/TranslatorContext.cs
index 3b88fdba..856b16b7 100644
--- a/Ryujinx.Graphics.Shader/Translation/TranslatorContext.cs
+++ b/Ryujinx.Graphics.Shader/Translation/TranslatorContext.cs
@@ -143,9 +143,9 @@ namespace Ryujinx.Graphics.Shader.Translation
_config.SetGeometryShaderLayerInputAttribute(attr);
}
- public void SetLastInVertexPipeline(bool hasFragment)
+ public void SetLastInVertexPipeline()
{
- _config.SetLastInVertexPipeline(hasFragment);
+ _config.SetLastInVertexPipeline();
}
public ShaderProgram Translate(TranslatorContext other = null)