summaryrefslogtreecommitdiffstats
path: root/source
diff options
context:
space:
mode:
Diffstat (limited to 'source')
-rw-r--r--source/slang/ir-insts.h21
-rw-r--r--source/slang/ir.cpp28
-rw-r--r--source/slang/lower-to-ir.cpp5
3 files changed, 45 insertions, 9 deletions
diff --git a/source/slang/ir-insts.h b/source/slang/ir-insts.h
index 05ccd76e7..6075c247c 100644
--- a/source/slang/ir-insts.h
+++ b/source/slang/ir-insts.h
@@ -712,7 +712,28 @@ struct IRBuilder
IRWitnessTable* lookupWitnessTable(Name* mangledName);
void registerWitnessTable(IRWitnessTable* table);
+
+ /// Create an empty basic block.
+ ///
+ /// The created block will not be inserted into the current
+ /// function; call `insertBlock()` to attach the block
+ /// at an appropriate point.
+ ///
IRBlock* createBlock();
+
+ /// Insert a block into the current function.
+ ///
+ /// This attaches the given `block` to the current function,
+ /// and makes it the current block for
+ /// new instructions that get emitted.
+ ///
+ void insertBlock(IRBlock* block);
+
+ /// Emit a new block into the current function.
+ ///
+ /// This function is equivalent to using `createBlock()`
+ /// and then `insertBlock()`.
+ ///
IRBlock* emitBlock();
diff --git a/source/slang/ir.cpp b/source/slang/ir.cpp
index 6e14edc1f..cc3350aef 100644
--- a/source/slang/ir.cpp
+++ b/source/slang/ir.cpp
@@ -2029,23 +2029,37 @@ namespace Slang
getBasicBlockType());
}
- IRBlock* IRBuilder::emitBlock()
+ void IRBuilder::insertBlock(IRBlock* block)
{
- // Create a block
- auto bb = createBlock();
-
// If we are emitting into a function
// (or another value with code), then
// append the block to the function and
// set this block as the new parent for
// subsequent instructions we insert.
+ //
+ // TODO: This should probably insert the block
+ // after the current "insert into" block if
+ // there is one. Right now we are always
+ // adding the block to the end of the list,
+ // which is technically valid (the ordering
+ // of blocks doesn't affect the CFG topology),
+ // but some later passes might assume the ordering
+ // is significant in representing the intent
+ // of the original code.
+ //
auto f = getFunc();
if (f)
{
- f->addBlock(bb);
- setInsertInto(bb);
+ f->addBlock(block);
+ setInsertInto(block);
}
- return bb;
+ }
+
+ IRBlock* IRBuilder::emitBlock()
+ {
+ auto block = createBlock();
+ insertBlock(block);
+ return block;
}
IRParam* IRBuilder::createParam(
diff --git a/source/slang/lower-to-ir.cpp b/source/slang/lower-to-ir.cpp
index 6cce469ea..806654ccb 100644
--- a/source/slang/lower-to-ir.cpp
+++ b/source/slang/lower-to-ir.cpp
@@ -4012,18 +4012,19 @@ struct DeclLoweringVisitor : DeclVisitor<DeclLoweringVisitor, LoweredValInfo>
// generating the code we actually care about, back in the original function.
auto builder = getBuilder();
+
auto initBlock = builder->createBlock();
auto afterBlock = builder->createBlock();
builder->emitIfElse(getSimpleVal(context, boolVal), afterBlock, initBlock, afterBlock);
- builder->setInsertInto(initBlock);
+ builder->insertBlock(initBlock);
LoweredValInfo initVal = lowerLValueExpr(context, initExpr);
assign(context, globalVal, initVal);
assign(context, boolVal, LoweredValInfo::simple(builder->getBoolValue(true)));
builder->emitBranch(afterBlock);
- builder->setInsertInto(afterBlock);
+ builder->insertBlock(afterBlock);
}
irGlobal->moveToEnd();