diff options
| author | Yong He <yonghe@outlook.com> | 2023-03-24 20:17:46 -0700 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2023-03-24 20:17:46 -0700 |
| commit | 666af0962b6ab41489a3a3287db83f77c2f6461a (patch) | |
| tree | 81a1247188ac03f1e8132e58ec31ae0f28c8c530 /source/slang/slang-lower-to-ir.cpp | |
| parent | 7292edbd3eba3da7e8490ad19169a7d18283057a (diff) | |
Switch to short circuiting semantics for scalar `?:` operator. (#2733)
Diffstat (limited to 'source/slang/slang-lower-to-ir.cpp')
| -rw-r--r-- | source/slang/slang-lower-to-ir.cpp | 37 |
1 files changed, 37 insertions, 0 deletions
diff --git a/source/slang/slang-lower-to-ir.cpp b/source/slang/slang-lower-to-ir.cpp index 9c27beb58..7144b3450 100644 --- a/source/slang/slang-lower-to-ir.cpp +++ b/source/slang/slang-lower-to-ir.cpp @@ -4003,6 +4003,43 @@ struct ExprLoweringVisitorBase : ExprVisitor<Derived, LoweredValInfo> return e; } + LoweredValInfo visitSelectExpr(SelectExpr* expr) + { + // A vector typed `select` expr will turn into a normal `select` op. + if (!as<BasicExpressionType>(expr->arguments[0]->type.type)) + { + return visitInvokeExpr(expr); + } + + // In global scope? This is a constant, and we should emit as `select` inst. + if (!getParentFunc(context->irBuilder->getInsertLoc().getInst())) + { + return visitInvokeExpr(expr); + } + + // A scalar typed `select` expr will turn into an if-else to implement short circuiting + // semantics. + auto builder = context->irBuilder; + auto thenBlock = builder->createBlock(); + auto elseBlock = builder->createBlock(); + auto afterBlock = builder->createBlock(); + auto irCond = getSimpleVal(context, lowerRValueExpr(context, expr->arguments[0])); + builder->emitIfElse(irCond, thenBlock, elseBlock, afterBlock); + builder->insertBlock(thenBlock); + builder->setInsertInto(thenBlock); + auto trueVal = getSimpleVal(context, lowerRValueExpr(context, expr->arguments[1])); + builder->emitBranch(afterBlock, 1, &trueVal); + builder->insertBlock(elseBlock); + builder->setInsertInto(elseBlock); + auto falseVal = getSimpleVal(context, lowerRValueExpr(context, expr->arguments[2])); + builder->emitBranch(afterBlock, 1, &falseVal); + builder->insertBlock(afterBlock); + builder->setInsertInto(afterBlock); + auto paramType = lowerType(context, expr->type.type); + auto result = builder->emitParam(paramType); + return LoweredValInfo::simple(result); + } + LoweredValInfo visitInvokeExpr(InvokeExpr* expr) { return visitInvokeExprImpl(expr, TryClauseEnvironment()); |
