summaryrefslogtreecommitdiffstats
path: root/source
diff options
context:
space:
mode:
authorTim Foley <tfoleyNV@users.noreply.github.com>2018-03-30 16:53:07 -0700
committerGitHub <noreply@github.com>2018-03-30 16:53:07 -0700
commitbd66d4f90086eeff339f076f8cedfbf78e1989b6 (patch)
tree4fe943e2bc47015ea39444fb025e7b2f533dcac8 /source
parent87c50cf1644454cdc9e7f6d1262bee29bfc86e80 (diff)
Fix several issues discovered by Falcor (#467)
Fixes #466 Most of these are Vulkan-related regressions. * Kludge the definition of `GroupMemoryBarrierWithGroupSync()` for GLSL so that it works around parentheses that the emit logic now introduces. * Don't emit `static` for global constants when targetting GLSL * Emit the `flat` modifier for varying input/output with integer type, when targetting GLSL * Avoid checking parameter default-value expressions more than once, because this can crash when the checking introduces syntax that is not expected to appear in the input AST
Diffstat (limited to 'source')
-rw-r--r--source/slang/check.cpp12
-rw-r--r--source/slang/emit.cpp53
-rw-r--r--source/slang/hlsl.meta.slang7
-rw-r--r--source/slang/hlsl.meta.slang.h7
4 files changed, 71 insertions, 8 deletions
diff --git a/source/slang/check.cpp b/source/slang/check.cpp
index b1df71428..eb15d0889 100644
--- a/source/slang/check.cpp
+++ b/source/slang/check.cpp
@@ -511,7 +511,11 @@ namespace Slang
// Use visitor pattern to dispatch to correct case
DeclVisitor::dispatch(decl);
- decl->SetCheckState(state);
+
+ if(state > decl->checkState)
+ {
+ decl->SetCheckState(state);
+ }
}
void EnusreAllDeclsRec(RefPtr<Decl> decl)
@@ -2839,6 +2843,8 @@ namespace Slang
paramDecl->type = typeExpr;
}
+ paramDecl->SetCheckState(DeclCheckState::CheckedHeader);
+
// The "initializer" expression for a parameter represents
// a default argument value to use if an explicit one is
// not supplied.
@@ -2857,6 +2863,8 @@ namespace Slang
// to other parameters of the same function (or maybe
// only the parameters to its left...).
}
+
+ paramDecl->SetCheckState(DeclCheckState::Checked);
}
void VisitFunctionDeclaration(FuncDecl *functionNode)
@@ -2870,7 +2878,7 @@ namespace Slang
HashSet<Name*> paraNames;
for (auto & para : functionNode->GetParameters())
{
- checkDecl(para);
+ EnsureDecl(para, DeclCheckState::CheckedHeader);
if (paraNames.Contains(para->getName()))
{
diff --git a/source/slang/emit.cpp b/source/slang/emit.cpp
index bed2488a1..f6a87fcfa 100644
--- a/source/slang/emit.cpp
+++ b/source/slang/emit.cpp
@@ -4545,6 +4545,35 @@ struct EmitVisitor
}
+ // Emit the `flat` qualifier if the underlying type
+ // of the variable is an integer type.
+ void maybeEmitGLSLFlatModifier(
+ EmitContext*,
+ Type* valueType)
+ {
+ auto tt = valueType;
+ if(auto vecType = tt->As<VectorExpressionType>())
+ tt = vecType->elementType;
+ if(auto vecType = tt->As<MatrixExpressionType>())
+ tt = vecType->getElementType();
+
+ auto baseType = tt->As<BasicExpressionType>();
+ if(!baseType)
+ return;
+
+ switch(baseType->baseType)
+ {
+ default:
+ break;
+
+ case BaseType::Int:
+ case BaseType::UInt:
+ case BaseType::UInt64:
+ Emit("flat ");
+ break;
+ }
+ }
+
void emitIRVarModifiers(
EmitContext* ctx,
VarLayout* layout,
@@ -4601,12 +4630,24 @@ struct EmitVisitor
emit("uniform ");
break;
- case LayoutResourceKind::VertexInput:
- emit("in ");
+ case LayoutResourceKind::VaryingInput:
+ {
+ emit("in ");
+ if(layout->stage == Stage::Fragment)
+ {
+ maybeEmitGLSLFlatModifier(ctx, valueType);
+ }
+ }
break;
case LayoutResourceKind::FragmentOutput:
- emit("out ");
+ {
+ emit("out ");
+ if(layout->stage != Stage::Fragment)
+ {
+ maybeEmitGLSLFlatModifier(ctx, valueType);
+ }
+ }
break;
default:
@@ -5145,7 +5186,11 @@ struct EmitVisitor
{
auto valType = valDecl->getDataType();
- emit("static const ");
+ if( ctx->shared->target != CodeGenTarget::GLSL )
+ {
+ emit("static ");
+ }
+ emit("const ");
emitIRType(ctx, valType, getIRName(valDecl));
if (valDecl->getFirstBlock())
diff --git a/source/slang/hlsl.meta.slang b/source/slang/hlsl.meta.slang
index 7356eccbe..75d9a3d33 100644
--- a/source/slang/hlsl.meta.slang
+++ b/source/slang/hlsl.meta.slang
@@ -583,7 +583,12 @@ float2 GetRenderTargetSamplePosition(int Index);
__target_intrinsic(glsl, "groupMemoryBarrier")
void GroupMemoryBarrier();
-__target_intrinsic(glsl, "groupMemoryBarrier(); barrier()")
+// Note: the unmatched parentheses in the GLSL lowering are
+// to cancel out the parens that the emit logic uses, so that
+// we can emit this as if it were an expression.
+//
+// TODO: investigate whether we can just use "operator comma" here.
+__target_intrinsic(glsl, "groupMemoryBarrier()); (barrier()")
void GroupMemoryBarrierWithGroupSync();
// Atomics
diff --git a/source/slang/hlsl.meta.slang.h b/source/slang/hlsl.meta.slang.h
index 134a3172f..4d241041b 100644
--- a/source/slang/hlsl.meta.slang.h
+++ b/source/slang/hlsl.meta.slang.h
@@ -589,7 +589,12 @@ SLANG_RAW("// Group memory barrier\n")
SLANG_RAW("__target_intrinsic(glsl, \"groupMemoryBarrier\")\n")
SLANG_RAW("void GroupMemoryBarrier();\n")
SLANG_RAW("\n")
-SLANG_RAW("__target_intrinsic(glsl, \"groupMemoryBarrier(); barrier()\")\n")
+SLANG_RAW("// Note: the unmatched parentheses in the GLSL lowering are\n")
+SLANG_RAW("// to cancel out the parens that the emit logic uses, so that\n")
+SLANG_RAW("// we can emit this as if it were an expression.\n")
+SLANG_RAW("//\n")
+SLANG_RAW("// TODO: investigate whether we can just use \"operator comma\" here.\n")
+SLANG_RAW("__target_intrinsic(glsl, \"groupMemoryBarrier()); (barrier()\")\n")
SLANG_RAW("void GroupMemoryBarrierWithGroupSync();\n")
SLANG_RAW("\n")
SLANG_RAW("// Atomics\n")