[tint][ir][ToProgram] Emit 'else if' instead of 'else { if'
Bug: tint:1902
Change-Id: If49a7fd71d72cd562fc49957a5715ea7eefc8b4d
Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/133140
Kokoro: Ben Clayton <bclayton@google.com>
Reviewed-by: Dan Sinclair <dsinclair@chromium.org>
Commit-Queue: Ben Clayton <bclayton@google.com>
diff --git a/src/tint/ir/to_program.cc b/src/tint/ir/to_program.cc
index a59146e..972f526 100644
--- a/src/tint/ir/to_program.cc
+++ b/src/tint/ir/to_program.cc
@@ -116,10 +116,27 @@
const ast::IfStatement* If(const ir::If* i) {
auto* cond = Expr(i->condition);
auto* t = FlowNodeGraph(i->true_.target, i->merge.target);
+ if (!t) {
+ return nullptr;
+ }
if (!IsEmpty(i->false_.target, i->merge.target)) {
- // TODO(crbug.com/tint/1902): Merge if else
- auto* f = FlowNodeGraph(i->false_.target, i->merge.target);
- return b.If(cond, t, b.Else(f));
+ // If the else target is an if flow node with the same merge target as this if, then
+ // emit an 'else if' instead of a block statement for the else.
+ if (auto* else_if = As<ir::If>(NextNonEmptyNode(i->false_.target));
+ else_if &&
+ NextNonEmptyNode(i->merge.target) == NextNonEmptyNode(else_if->merge.target)) {
+ auto* f = If(else_if);
+ if (!f) {
+ return nullptr;
+ }
+ return b.If(cond, t, b.Else(f));
+ } else {
+ auto* f = FlowNodeGraph(i->false_.target, i->merge.target);
+ if (!f) {
+ return nullptr;
+ }
+ return b.If(cond, t, b.Else(f));
+ }
}
return b.If(cond, t);
}
@@ -139,6 +156,21 @@
return true;
}
+ /// @return the next flow node that isn't an empty block
+ const ir::FlowNode* NextNonEmptyNode(const ir::FlowNode* node) {
+ while (node) {
+ if (auto* block = node->As<ir::Block>()) {
+ if (block->instructions.Length() > 0) {
+ return node;
+ }
+ node = block->branch.target;
+ } else {
+ return node;
+ }
+ }
+ return nullptr;
+ }
+
const ast::Statement* Stmt(const ir::Instruction* inst) {
return Switch(
inst, //
diff --git a/src/tint/ir/to_program_roundtrip_test.cc b/src/tint/ir/to_program_roundtrip_test.cc
index e62646c..dd04ab3 100644
--- a/src/tint/ir/to_program_roundtrip_test.cc
+++ b/src/tint/ir/to_program_roundtrip_test.cc
@@ -152,28 +152,6 @@
b();
}
}
-)",
- R"(
-fn a() {
-}
-
-fn b() {
-}
-
-fn c() {
-}
-
-fn f() {
- var cond_a : bool = true;
- var cond_b : bool = true;
- if (cond_a) {
- a();
- } else {
- if (cond_b) {
- b();
- }
- }
-}
)");
}
} // namespace