summaryrefslogtreecommitdiffstats
path: root/source/slang/slang-ir-validate.cpp
diff options
context:
space:
mode:
authorYong He <yonghe@outlook.com>2022-02-25 20:49:31 -0800
committerGitHub <noreply@github.com>2022-02-25 20:49:31 -0800
commitc31577953d5041c82375c22d847c2eba06106c58 (patch)
treebc685a8b63fc13cb85d160ae13df950056ca6e91 /source/slang/slang-ir-validate.cpp
parent8990d270e3a0c01b1f7abbf4f79556c5ef82a096 (diff)
Improved SCCP, inlining and resource specialization passes, legalize `ImageSubscript` for GLSL (#2146)
Diffstat (limited to 'source/slang/slang-ir-validate.cpp')
-rw-r--r--source/slang/slang-ir-validate.cpp49
1 files changed, 49 insertions, 0 deletions
diff --git a/source/slang/slang-ir-validate.cpp b/source/slang/slang-ir-validate.cpp
index ffadf33cf..e8da87187 100644
--- a/source/slang/slang-ir-validate.cpp
+++ b/source/slang/slang-ir-validate.cpp
@@ -196,6 +196,50 @@ namespace Slang
}
}
+ void validateCodeBody(IRValidateContext* context, IRGlobalValueWithCode* code)
+ {
+ HashSet<IRBlock*> blocks;
+ for (auto block : code->getBlocks())
+ blocks.Add(block);
+ auto validateBranchTarget = [&](IRInst* inst, IRBlock* target)
+ {
+ validate(
+ context,
+ blocks.Contains(target),
+ inst,
+ "branch inst must have a valid target block that is defined within the same "
+ "scope.");
+ };
+ for (auto block : code->getBlocks())
+ {
+ auto terminator = block->getTerminator();
+ validate(context, terminator, block, "block must have valid terminator inst.");
+ switch (terminator->getOp())
+ {
+ case kIROp_conditionalBranch:
+ validateBranchTarget(
+ terminator, as<IRConditionalBranch>(terminator)->getTrueBlock());
+ validateBranchTarget(
+ terminator, as<IRConditionalBranch>(terminator)->getFalseBlock());
+ break;
+ case kIROp_loop:
+ case kIROp_unconditionalBranch:
+ validateBranchTarget(terminator, as<IRUnconditionalBranch>(terminator)->getTargetBlock());
+ break;
+ case kIROp_Switch:
+ {
+ auto switchInst = as<IRSwitch>(terminator);
+ for (UInt i = 0; i < switchInst->getCaseCount(); i++)
+ {
+ validateBranchTarget(switchInst, switchInst->getCaseLabel(i));
+ }
+ validateBranchTarget(switchInst, switchInst->getDefaultLabel());
+ validateBranchTarget(switchInst, switchInst->getBreakLabel());
+ }
+ }
+ }
+ }
+
void validateIRInst(
IRValidateContext* context,
IRInst* inst)
@@ -207,6 +251,11 @@ namespace Slang
// If `inst` is itself a parent instruction, then we need to recursively
// validate its children.
validateIRInstChildren(context, inst);
+
+ if (auto code = as<IRGlobalValueWithCode>(inst))
+ {
+ validateCodeBody(context, code);
+ }
}
void validateIRModule(IRModule* module, DiagnosticSink* sink)