Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/KhronosGroup/SPIRV-Cross.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorHans-Kristian Arntzen <post@arntzen-software.no>2019-12-10 16:28:33 +0300
committerGitHub <noreply@github.com>2019-12-10 16:28:33 +0300
commitf912c32898dbf558635c9d5a2d50ff887c1402ae (patch)
tree302f9de74cff0172857b0c864639f954d2d69cf2
parent363035c79828a79d3980cedcce4109434af93b33 (diff)
parent7c1e34f3b9ad2d249dcf01b6fa6a30cdc7911755 (diff)
Merge pull request #1235 from KhronosGroup/patch-input-array-fix2019-12-15
GLSL: Fix array of input patch variables.
-rw-r--r--reference/opt/shaders/desktop-only/tesc/basic.desktop.sso.tesc2
-rw-r--r--reference/opt/shaders/desktop-only/tese/triangle.desktop.sso.tese2
-rw-r--r--reference/opt/shaders/tese/patch-input-array.tese10
-rw-r--r--reference/shaders/desktop-only/tesc/basic.desktop.sso.tesc2
-rw-r--r--reference/shaders/desktop-only/tese/triangle.desktop.sso.tese2
-rw-r--r--reference/shaders/tese/patch-input-array.tese10
-rw-r--r--shaders/tese/patch-input-array.tese9
-rw-r--r--spirv_glsl.cpp37
8 files changed, 59 insertions, 15 deletions
diff --git a/reference/opt/shaders/desktop-only/tesc/basic.desktop.sso.tesc b/reference/opt/shaders/desktop-only/tesc/basic.desktop.sso.tesc
index 5e958256..c51699db 100644
--- a/reference/opt/shaders/desktop-only/tesc/basic.desktop.sso.tesc
+++ b/reference/opt/shaders/desktop-only/tesc/basic.desktop.sso.tesc
@@ -4,7 +4,7 @@ layout(vertices = 1) out;
in gl_PerVertex
{
vec4 gl_Position;
-} gl_in[gl_MaxPatchVertices];
+} gl_in[];
out gl_PerVertex
{
diff --git a/reference/opt/shaders/desktop-only/tese/triangle.desktop.sso.tese b/reference/opt/shaders/desktop-only/tese/triangle.desktop.sso.tese
index 31027dae..c9bacd46 100644
--- a/reference/opt/shaders/desktop-only/tese/triangle.desktop.sso.tese
+++ b/reference/opt/shaders/desktop-only/tese/triangle.desktop.sso.tese
@@ -4,7 +4,7 @@ layout(triangles, cw, fractional_even_spacing) in;
in gl_PerVertex
{
vec4 gl_Position;
-} gl_in[gl_MaxPatchVertices];
+} gl_in[];
out gl_PerVertex
{
diff --git a/reference/opt/shaders/tese/patch-input-array.tese b/reference/opt/shaders/tese/patch-input-array.tese
new file mode 100644
index 00000000..413d8b39
--- /dev/null
+++ b/reference/opt/shaders/tese/patch-input-array.tese
@@ -0,0 +1,10 @@
+#version 450
+layout(quads, ccw, equal_spacing) in;
+
+layout(location = 0) patch in float P[4];
+
+void main()
+{
+ gl_Position = vec4(P[0], P[1], P[2], P[3]);
+}
+
diff --git a/reference/shaders/desktop-only/tesc/basic.desktop.sso.tesc b/reference/shaders/desktop-only/tesc/basic.desktop.sso.tesc
index 5e958256..c51699db 100644
--- a/reference/shaders/desktop-only/tesc/basic.desktop.sso.tesc
+++ b/reference/shaders/desktop-only/tesc/basic.desktop.sso.tesc
@@ -4,7 +4,7 @@ layout(vertices = 1) out;
in gl_PerVertex
{
vec4 gl_Position;
-} gl_in[gl_MaxPatchVertices];
+} gl_in[];
out gl_PerVertex
{
diff --git a/reference/shaders/desktop-only/tese/triangle.desktop.sso.tese b/reference/shaders/desktop-only/tese/triangle.desktop.sso.tese
index 31027dae..c9bacd46 100644
--- a/reference/shaders/desktop-only/tese/triangle.desktop.sso.tese
+++ b/reference/shaders/desktop-only/tese/triangle.desktop.sso.tese
@@ -4,7 +4,7 @@ layout(triangles, cw, fractional_even_spacing) in;
in gl_PerVertex
{
vec4 gl_Position;
-} gl_in[gl_MaxPatchVertices];
+} gl_in[];
out gl_PerVertex
{
diff --git a/reference/shaders/tese/patch-input-array.tese b/reference/shaders/tese/patch-input-array.tese
new file mode 100644
index 00000000..413d8b39
--- /dev/null
+++ b/reference/shaders/tese/patch-input-array.tese
@@ -0,0 +1,10 @@
+#version 450
+layout(quads, ccw, equal_spacing) in;
+
+layout(location = 0) patch in float P[4];
+
+void main()
+{
+ gl_Position = vec4(P[0], P[1], P[2], P[3]);
+}
+
diff --git a/shaders/tese/patch-input-array.tese b/shaders/tese/patch-input-array.tese
new file mode 100644
index 00000000..741b2c3b
--- /dev/null
+++ b/shaders/tese/patch-input-array.tese
@@ -0,0 +1,9 @@
+#version 450
+
+layout(quads) in;
+layout(location = 0) patch in float P[4];
+
+void main()
+{
+ gl_Position = vec4(P[0], P[1], P[2], P[3]);
+}
diff --git a/spirv_glsl.cpp b/spirv_glsl.cpp
index f4cfd4f2..f6a1b8b6 100644
--- a/spirv_glsl.cpp
+++ b/spirv_glsl.cpp
@@ -2104,9 +2104,32 @@ void CompilerGLSL::emit_interface_block(const SPIRVariable &var)
else
{
add_resource_name(var.self);
+
+ // Tessellation control and evaluation shaders must have either gl_MaxPatchVertices or unsized arrays for input arrays.
+ // Opt for unsized as it's the more "correct" variant to use.
+ bool control_point_input_array = type.storage == StorageClassInput &&
+ !type.array.empty() && !has_decoration(var.self, DecorationPatch) &&
+ (get_entry_point().model == ExecutionModelTessellationControl ||
+ get_entry_point().model == ExecutionModelTessellationEvaluation);
+
+ uint32_t old_array_size = 0;
+ bool old_array_size_literal = true;
+
+ if (control_point_input_array)
+ {
+ swap(type.array.back(), old_array_size);
+ swap(type.array_size_literal.back(), old_array_size_literal);
+ }
+
statement(layout_for_variable(var), to_qualifiers_glsl(var.self),
variable_decl(type, to_name(var.self), var.self), ";");
+ if (control_point_input_array)
+ {
+ swap(type.array.back(), old_array_size);
+ swap(type.array_size_literal.back(), old_array_size_literal);
+ }
+
// If a StorageClassOutput variable has an initializer, we need to initialize it in main().
if (var.storage == StorageClassOutput && var.initializer)
{
@@ -2478,7 +2501,6 @@ void CompilerGLSL::emit_declared_builtin_block(StorageClass storage, ExecutionMo
if (emitted_builtins.get(BuiltInCullDistance))
statement("float gl_CullDistance[", cull_distance_size, "];");
- bool tessellation = model == ExecutionModelTessellationEvaluation || model == ExecutionModelTessellationControl;
if (builtin_array)
{
// Make sure the array has a supported name in the code.
@@ -2490,7 +2512,7 @@ void CompilerGLSL::emit_declared_builtin_block(StorageClass storage, ExecutionMo
if (model == ExecutionModelTessellationControl && storage == StorageClassOutput)
end_scope_decl(join(to_name(block_var->self), "[", get_entry_point().output_vertices, "]"));
else
- end_scope_decl(join(to_name(block_var->self), tessellation ? "[gl_MaxPatchVertices]" : "[]"));
+ end_scope_decl(join(to_name(block_var->self), "[]"));
}
else
end_scope_decl();
@@ -10794,14 +10816,6 @@ string CompilerGLSL::to_array_size(const SPIRType &type, uint32_t index)
{
assert(type.array.size() == type.array_size_literal.size());
- // Tessellation control and evaluation shaders must have either gl_MaxPatchVertices or unsized arrays for input arrays.
- // Opt for unsized as it's the more "correct" variant to use.
- if (type.storage == StorageClassInput &&
- (get_entry_point().model == ExecutionModelTessellationControl ||
- get_entry_point().model == ExecutionModelTessellationEvaluation) &&
- index == uint32_t(type.array.size() - 1))
- return "";
-
auto &size = type.array[index];
if (!type.array_size_literal[index])
return to_expression(size);
@@ -12795,13 +12809,14 @@ void CompilerGLSL::unroll_array_from_complex_load(uint32_t target_id, uint32_t s
auto builtin = BuiltIn(get_decoration(var->self, DecorationBuiltIn));
bool is_builtin = is_builtin_variable(*var) && (builtin == BuiltInPointSize || builtin == BuiltInPosition);
bool is_tess = is_tessellation_shader();
+ bool is_patch = has_decoration(var->self, DecorationPatch);
// Tessellation input arrays are special in that they are unsized, so we cannot directly copy from it.
// We must unroll the array load.
// For builtins, we couldn't catch this case normally,
// because this is resolved in the OpAccessChain in most cases.
// If we load the entire array, we have no choice but to unroll here.
- if (is_builtin || is_tess)
+ if (!is_patch && (is_builtin || is_tess))
{
auto new_expr = join("_", target_id, "_unrolled");
statement(variable_decl(type, new_expr, target_id), ";");