[ir] Add protobuf support for constexpr_if

Missed this one when adding override support.

Bug: 402760393
Change-Id: I2c7d0899d75dceefa25a230f3002c02154e76c3a
Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/312035
Reviewed-by: dan sinclair <dsinclair@chromium.org>
Commit-Queue: James Price <jrprice@google.com>
Commit-Queue: dan sinclair <dsinclair@chromium.org>
Auto-Submit: James Price <jrprice@google.com>
diff --git a/src/tint/lang/core/ir/binary/decode.cc b/src/tint/lang/core/ir/binary/decode.cc
index 9b9cfe6..d36dac8 100644
--- a/src/tint/lang/core/ir/binary/decode.cc
+++ b/src/tint/lang/core/ir/binary/decode.cc
@@ -453,6 +453,9 @@
             case pb::Instruction::KindCase::kBuiltinCall:
                 inst_out = CreateInstructionBuiltinCall(inst_in.builtin_call());
                 break;
+            case pb::Instruction::KindCase::kConstExprIf:
+                inst_out = CreateInstructionConstExprIf(inst_in.const_expr_if());
+                break;
             case pb::Instruction::KindCase::kConstruct:
                 inst_out = CreateInstructionConstruct(inst_in.construct());
                 break;
@@ -634,6 +637,13 @@
         return if_out;
     }
 
+    ir::If* CreateInstructionConstExprIf(const pb::InstructionConstExprIf& if_in) {
+        auto* if_out = mod_out_.CreateInstruction<ir::ConstExprIf>();
+        if_out->SetTrue(if_in.has_true_() ? Block(if_in.true_()) : b.Block());
+        if_out->SetFalse(if_in.has_false_() ? Block(if_in.false_()) : b.Block());
+        return if_out;
+    }
+
     ir::Let* CreateInstructionLet(const pb::InstructionLet&) {
         return mod_out_.CreateInstruction<ir::Let>();
     }
diff --git a/src/tint/lang/core/ir/binary/encode.cc b/src/tint/lang/core/ir/binary/encode.cc
index 59d8f48..d77e256 100644
--- a/src/tint/lang/core/ir/binary/encode.cc
+++ b/src/tint/lang/core/ir/binary/encode.cc
@@ -37,6 +37,7 @@
 #include "src/tint/lang/core/enums.h"
 #include "src/tint/lang/core/ir/access.h"
 #include "src/tint/lang/core/ir/break_if.h"
+#include "src/tint/lang/core/ir/constexpr_if.h"
 #include "src/tint/lang/core/ir/construct.h"
 #include "src/tint/lang/core/ir/continue.h"
 #include "src/tint/lang/core/ir/convert.h"
@@ -225,6 +226,9 @@
                 InstructionBuiltinCall(*inst_out.mutable_builtin_call(), i);
             },
             [&](const ir::CoreUnary* i) { InstructionUnary(*inst_out.mutable_unary(), i); },
+            [&](const ir::ConstExprIf* i) {
+                InstructionConstExprIf(*inst_out.mutable_const_expr_if(), i);
+            },
             [&](const ir::Construct* i) { InstructionConstruct(*inst_out.mutable_construct(), i); },
             [&](const ir::Continue* i) { InstructionContinue(*inst_out.mutable_continue_(), i); },
             [&](const ir::Convert* i) { InstructionConvert(*inst_out.mutable_convert(), i); },
@@ -300,6 +304,16 @@
         }
     }
 
+    void InstructionConstExprIf(pb::InstructionConstExprIf& const_expr_if_out,
+                                const ir::ConstExprIf* const_expr_if_in) {
+        if (auto* block = const_expr_if_in->True()) {
+            const_expr_if_out.set_true_(Block(block));
+        }
+        if (auto* block = const_expr_if_in->False()) {
+            const_expr_if_out.set_false_(Block(block));
+        }
+    }
+
     void InstructionDiscard(pb::InstructionDiscard&, const ir::Discard*) {}
 
     void InstructionExitIf(pb::InstructionExitIf&, const ir::ExitIf*) {}
diff --git a/src/tint/lang/core/ir/binary/roundtrip_test.cc b/src/tint/lang/core/ir/binary/roundtrip_test.cc
index 8e85f93..cbfdab0 100644
--- a/src/tint/lang/core/ir/binary/roundtrip_test.cc
+++ b/src/tint/lang/core/ir/binary/roundtrip_test.cc
@@ -783,6 +783,24 @@
     RUN_TEST();
 }
 
+TEST_F(IRBinaryRoundtripTest, Override_ConstExprIf) {
+    b.Append(b.ir.root_block, [&] {
+        auto* o1 = b.Override(ty.u32());
+        auto* o2 = b.Override(ty.u32());
+        auto* if_ = b.ConstExprIf(b.Equal(o2, 0_u));
+        auto* result = b.InstructionResult<u32>();
+        if_->SetResult(result);
+        b.Append(if_->True(), [&] {  //
+            b.ExitIf(if_, o1);
+        });
+        b.Append(if_->False(), [&] {  //
+            b.ExitIf(if_, b.Divide(o1, o2));
+        });
+        b.Override("o3", result);
+    });
+    RUN_TEST();
+}
+
 TEST_F(IRBinaryRoundtripTest, Override_WorkgroupSize) {
     b.Append(b.ir.root_block, [&] {
         auto* o = b.Override(ty.u32());
diff --git a/src/tint/utils/protos/ir/ir.proto b/src/tint/utils/protos/ir/ir.proto
index 79d8bd7..d444267 100644
--- a/src/tint/utils/protos/ir/ir.proto
+++ b/src/tint/utils/protos/ir/ir.proto
@@ -345,6 +345,7 @@
         InstructionBreakIf break_if = 28;
         InstructionUnreachable unreachable = 29;
         InstructionOverride override = 30;
+        InstructionConstExprIf const_expr_if = 31;
     }
     reserved 9;
     reserved "bitcast";
@@ -401,6 +402,11 @@
     optional uint32 false = 2;  // Module.blocks
 }
 
+message InstructionConstExprIf {
+    optional uint32 true = 1;   // Module.blocks
+    optional uint32 false = 2;  // Module.blocks
+}
+
 message InstructionSwitch {
     repeated SwitchCase cases = 1;  // Module.blocks
 }