summaryrefslogtreecommitdiffstats
path: root/source/slang/slang-ir-variable-scope-correction.cpp
diff options
context:
space:
mode:
authorEllie Hermaszewska <ellieh@nvidia.com>2024-10-29 14:49:26 +0800
committerGitHub <noreply@github.com>2024-10-29 14:49:26 +0800
commitf65d756bff8d4c5cbc15bd0322a2ae8e6b896a21 (patch)
treeea1d61342cd29368e19135000ec2948813096205 /source/slang/slang-ir-variable-scope-correction.cpp
parenta729c15e9dce9f5116a38afc66329ab2ca4cea54 (diff)
format
* format * Minor test fixes * enable checking cpp format in ci
Diffstat (limited to 'source/slang/slang-ir-variable-scope-correction.cpp')
-rw-r--r--source/slang/slang-ir-variable-scope-correction.cpp120
1 files changed, 70 insertions, 50 deletions
diff --git a/source/slang/slang-ir-variable-scope-correction.cpp b/source/slang/slang-ir-variable-scope-correction.cpp
index e8e8f70a1..bc425a3ba 100644
--- a/source/slang/slang-ir-variable-scope-correction.cpp
+++ b/source/slang/slang-ir-variable-scope-correction.cpp
@@ -1,10 +1,10 @@
-#include "slang-ir-insts.h"
-#include "slang-ir.h"
-#include "slang-ir-clone.h"
+#include "slang-ir-variable-scope-correction.h"
+#include "slang-ir-clone.h"
#include "slang-ir-dominators.h"
-#include "slang-ir-variable-scope-correction.h"
+#include "slang-ir-insts.h"
#include "slang-ir-util.h"
+#include "slang-ir.h"
namespace Slang
{
@@ -12,11 +12,12 @@ namespace Slang
bool isCPUTarget(TargetRequest* targetReq);
bool isCUDATarget(TargetRequest* targetReq);
-namespace { // anonymous
+namespace
+{ // anonymous
struct VariableScopeCorrectionContext
{
- VariableScopeCorrectionContext(IRModule* module, TargetRequest* targetReq):
- m_module(module), m_builder(module), m_targetReq(targetReq)
+ VariableScopeCorrectionContext(IRModule* module, TargetRequest* targetReq)
+ : m_module(module), m_builder(module), m_targetReq(targetReq)
{
}
@@ -24,13 +25,20 @@ struct VariableScopeCorrectionContext
/// Process a function in the module
void _processFunction(IRFunc* funcInst);
- void _processInstruction(IRDominatorTree* dominatorTree, IRInst* instAfterParam,
- IRInst* originInst, const List<IRLoop*>& loopHeaderList, List<IRInst*>& workList);
+ void _processInstruction(
+ IRDominatorTree* dominatorTree,
+ IRInst* instAfterParam,
+ IRInst* originInst,
+ const List<IRLoop*>& loopHeaderList,
+ List<IRInst*>& workList);
void _processStorableInst(IRInst* insertLoc, IRInst* inst, const List<IRUse*>& outOfScopeUses);
void _processUnstorableInst(IRInst* inst, const List<IRUse*>& outOfScopeUser);
bool _isStorableType(IRType* inst);
- bool _isOutOfScopeUse(IRInst* inst, IRDominatorTree* domTree, const List<IRLoop*>& loopHeaderList);
+ bool _isOutOfScopeUse(
+ IRInst* inst,
+ IRDominatorTree* domTree,
+ const List<IRLoop*>& loopHeaderList);
IRModule* m_module;
IRBuilder m_builder;
@@ -62,12 +70,13 @@ void VariableScopeCorrectionContext::_processFunction(IRFunc* funcInst)
// traverse all blocks in the function
for (auto block : funcInst->getBlocks())
{
- // Traverse all the dominators of a given block to check whether this given block is in a loop region.
- // Loop region blocks are the blocks that are dominated by the loop header block
- // but not dominated by the loop break block.
+ // Traverse all the dominators of a given block to check whether this given block is in a
+ // loop region. Loop region blocks are the blocks that are dominated by the loop header
+ // block but not dominated by the loop break block.
auto dominatorBlock = dominatorTree->getImmediateDominator(block);
List<IRLoop*> loopHeaderList;
- for (; dominatorBlock; dominatorBlock = dominatorTree->getImmediateDominator(dominatorBlock))
+ for (; dominatorBlock;
+ dominatorBlock = dominatorTree->getImmediateDominator(dominatorBlock))
{
// Find if the block is loop header block
if (auto loopHeader = as<IRLoop>(dominatorBlock->getTerminator()))
@@ -75,7 +84,8 @@ void VariableScopeCorrectionContext::_processFunction(IRFunc* funcInst)
// Get the break block of the loop and check if such block
auto breakBlock = loopHeader->getBreakBlock();
- // Check if the current block is dominated by the break block. If so, it means that the block is in the loop region.
+ // Check if the current block is dominated by the break block. If so, it means that
+ // the block is in the loop region.
if (!dominatorTree->dominates(breakBlock, block))
{
loopHeaderList.add(loopHeader);
@@ -93,12 +103,13 @@ void VariableScopeCorrectionContext::_processFunction(IRFunc* funcInst)
// Traverse all the instructions in function.
for (auto block : funcInst->getBlocks())
{
- if(loopHeaderMap.containsKey(block))
+ if (loopHeaderMap.containsKey(block))
{
for (auto inst : block->getChildren())
{
List<IRInst*> instList;
- // Don't process the variable declaration instruction because the code is not emitted for them unless there is a use.
+ // Don't process the variable declaration instruction because the code is not
+ // emitted for them unless there is a use.
if (inst->getOp() == kIROp_Var)
{
continue;
@@ -110,7 +121,7 @@ void VariableScopeCorrectionContext::_processFunction(IRFunc* funcInst)
auto instAfterParam = funcInst->getFirstBlock()->getFirstOrdinaryInst();
- for(auto inst = workList.begin(); inst != workList.end(); inst++)
+ for (auto inst = workList.begin(); inst != workList.end(); inst++)
{
if (auto loopHeaderList = loopHeaderMap.tryGetValue(getBlock(*inst)))
{
@@ -125,14 +136,17 @@ void VariableScopeCorrectionContext::_processFunction(IRFunc* funcInst)
// it means that it was out of the loop, so it's out of the scope of the loop.
// Note the reason we use the loopHeaderList is because there could be nested loops, so we need to
// check all the loop headers from inner to outer.
-bool VariableScopeCorrectionContext::_isOutOfScopeUse(IRInst * userInst, IRDominatorTree* domTree, const List<IRLoop*>& loopHeaderList)
+bool VariableScopeCorrectionContext::_isOutOfScopeUse(
+ IRInst* userInst,
+ IRDominatorTree* domTree,
+ const List<IRLoop*>& loopHeaderList)
{
if (auto block = getBlock(userInst))
{
// If the use site of this instruction is dominated by the break block, it means that the
- // instruction is used after the break block, so we need to make that instruction available globally.
- // By doing so, we record all the users of this instructions.
- for(auto loopHeader : loopHeaderList)
+ // instruction is used after the break block, so we need to make that instruction available
+ // globally. By doing so, we record all the users of this instructions.
+ for (auto loopHeader : loopHeaderList)
{
auto breakBlock = loopHeader->getBreakBlock();
if (domTree->dominates(breakBlock, block))
@@ -144,13 +158,17 @@ bool VariableScopeCorrectionContext::_isOutOfScopeUse(IRInst * userInst, IRDomin
return false;
}
-void VariableScopeCorrectionContext::_processInstruction(IRDominatorTree* dominatorTree, IRInst* instAfterParam,
- IRInst* originInst, const List<IRLoop*>& loopHeaderList, List<IRInst*>& workList)
+void VariableScopeCorrectionContext::_processInstruction(
+ IRDominatorTree* dominatorTree,
+ IRInst* instAfterParam,
+ IRInst* originInst,
+ const List<IRLoop*>& loopHeaderList,
+ List<IRInst*>& workList)
{
List<IRUse*> outOfScopeUses;
- for (auto use = originInst->firstUse; use; use=use->nextUse)
+ for (auto use = originInst->firstUse; use; use = use->nextUse)
{
- if(_isOutOfScopeUse(use->getUser(), dominatorTree, loopHeaderList))
+ if (_isOutOfScopeUse(use->getUser(), dominatorTree, loopHeaderList))
{
outOfScopeUses.add(use);
}
@@ -159,7 +177,7 @@ void VariableScopeCorrectionContext::_processInstruction(IRDominatorTree* domina
if (outOfScopeUses.getCount() == 0)
return;
- if(_isStorableType(originInst->getDataType()))
+ if (_isStorableType(originInst->getDataType()))
{
_processStorableInst(instAfterParam, originInst, outOfScopeUses);
}
@@ -168,20 +186,24 @@ void VariableScopeCorrectionContext::_processInstruction(IRDominatorTree* domina
_processUnstorableInst(originInst, outOfScopeUses);
// After processing the user, we need to add operands of the instruction to the worklist
// for later processing.
- for(UInt idx = 0; idx < originInst->getOperandCount(); idx++)
+ for (UInt idx = 0; idx < originInst->getOperandCount(); idx++)
{
workList.add(originInst->getOperand(idx));
}
}
}
-void VariableScopeCorrectionContext::_processStorableInst(IRInst* insertLoc, IRInst* inst, const List<IRUse*>& outOfScopeUses)
+void VariableScopeCorrectionContext::_processStorableInst(
+ IRInst* insertLoc,
+ IRInst* inst,
+ const List<IRUse*>& outOfScopeUses)
{
auto type = inst->getDataType();
// store instruction must have a result type
SLANG_ASSERT(type);
- // declare a new variable at the beginning of the function used to store the result of the instruction
+ // declare a new variable at the beginning of the function used to store the result of the
+ // instruction
m_builder.setInsertBefore(insertLoc);
auto dstPtr = m_builder.emitVar(type);
@@ -190,8 +212,8 @@ void VariableScopeCorrectionContext::_processStorableInst(IRInst* insertLoc, IRI
m_builder.emitStore(dstPtr, inst);
// last, replace operands in the use site instruction with the new variable
- // Note, because "dstPtr" is a pointer type, we have to insert a load(dstPtr) instruction before use it.
- // Simply replace any operand with pointer could generate error code.
+ // Note, because "dstPtr" is a pointer type, we have to insert a load(dstPtr) instruction before
+ // use it. Simply replace any operand with pointer could generate error code.
for (auto use : outOfScopeUses)
{
m_builder.setInsertBefore(use->getUser());
@@ -200,7 +222,9 @@ void VariableScopeCorrectionContext::_processStorableInst(IRInst* insertLoc, IRI
}
}
-void VariableScopeCorrectionContext::_processUnstorableInst(IRInst* inst, const List<IRUse*>& outOfScopeUsers)
+void VariableScopeCorrectionContext::_processUnstorableInst(
+ IRInst* inst,
+ const List<IRUse*>& outOfScopeUsers)
{
IRCloneEnv cloneEnv;
auto clonedInst = cloneInst(&cloneEnv, &m_builder, inst);
@@ -226,27 +250,24 @@ bool VariableScopeCorrectionContext::_isStorableType(IRType* type)
if (as<IRBasicType>(type))
return true;
- switch(type->getOp())
+ switch (type->getOp())
{
- case kIROp_VectorType:
- case kIROp_MatrixType:
- case kIROp_StructType:
- return true;
- case kIROp_ArrayType:
- {
- if (auto arrayType = as<IRArrayTypeBase>(type))
- return _isStorableType(arrayType->getElementType());
- else
- return false;
- }
- case kIROp_UnsizedArrayType:
+ case kIROp_VectorType:
+ case kIROp_MatrixType:
+ case kIROp_StructType: return true;
+ case kIROp_ArrayType:
+ {
+ if (auto arrayType = as<IRArrayTypeBase>(type))
+ return _isStorableType(arrayType->getElementType());
+ else
return false;
- default:
- return false;
+ }
+ case kIROp_UnsizedArrayType: return false;
+ default: return false;
}
}
-} // anonymous
+} // namespace
void applyVariableScopeCorrection(IRModule* module, TargetRequest* targetReq)
{
@@ -256,4 +277,3 @@ void applyVariableScopeCorrection(IRModule* module, TargetRequest* targetReq)
}
} // namespace Slang
-