[tint] Move resolver/ctor_conv_intrinsic to core/intrinsic

Change-Id: Ic925f480bcc1d6101c197049db47a18f9c759b57
Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/144126
Reviewed-by: Dan Sinclair <dsinclair@chromium.org>
Kokoro: Kokoro <noreply+kokoro@google.com>
diff --git a/src/tint/BUILD.gn b/src/tint/BUILD.gn
index 0e2afb9..8768d4f 100644
--- a/src/tint/BUILD.gn
+++ b/src/tint/BUILD.gn
@@ -289,14 +289,14 @@
   sources = [
     "lang/core/constant/eval.cc",
     "lang/core/constant/eval.h",
+    "lang/core/intrinsic/ctor_conv.cc",
+    "lang/core/intrinsic/ctor_conv.h",
     "lang/core/intrinsic/table.cc",
     "lang/core/intrinsic/table.h",
     "lang/core/intrinsic/table.inl",
     "lang/wgsl/program/clone_context.cc",
     "lang/wgsl/program/program.cc",
     "lang/wgsl/program/program_builder.cc",
-    "lang/wgsl/resolver/ctor_conv_intrinsic.cc",
-    "lang/wgsl/resolver/ctor_conv_intrinsic.h",
     "lang/wgsl/resolver/dependency_graph.cc",
     "lang/wgsl/resolver/dependency_graph.h",
     "lang/wgsl/resolver/resolve.cc",
diff --git a/src/tint/CMakeLists.txt b/src/tint/CMakeLists.txt
index c670633..4bc52e6 100644
--- a/src/tint/CMakeLists.txt
+++ b/src/tint/CMakeLists.txt
@@ -592,7 +592,7 @@
 tint_generated(lang/core/interpolation_type BENCH TEST)
 tint_generated(lang/core/texel_format BENCH TEST)
 
-tint_generated(lang/wgsl/resolver/ctor_conv_intrinsic)
+tint_generated(lang/core/intrinsic/ctor_conv)
 tint_generated(lang/wgsl/sem/parameter_usage)
 
 if(UNIX)
diff --git a/src/tint/lang/core/intrinsic/ctor_conv.cc b/src/tint/lang/core/intrinsic/ctor_conv.cc
new file mode 100644
index 0000000..7abe148
--- /dev/null
+++ b/src/tint/lang/core/intrinsic/ctor_conv.cc
@@ -0,0 +1,71 @@
+// Copyright 2021 The Tint Authors.
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//     http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+////////////////////////////////////////////////////////////////////////////////
+// File generated by tools/src/cmd/gen
+// using the template:
+//   src/tint/lang/core/intrinsic/ctor_conv.cc.tmpl
+//
+// Do not modify this file directly
+////////////////////////////////////////////////////////////////////////////////
+
+#include "src/tint/lang/core/intrinsic/ctor_conv.h"
+
+namespace tint::core::intrinsic {
+
+const char* str(CtorConv i) {
+    switch (i) {
+        case CtorConv::kNone:
+            return "<none>";
+        case CtorConv::kI32:
+            return "i32";
+        case CtorConv::kU32:
+            return "u32";
+        case CtorConv::kF32:
+            return "f32";
+        case CtorConv::kF16:
+            return "f16";
+        case CtorConv::kBool:
+            return "bool";
+        case CtorConv::kVec2:
+            return "vec2";
+        case CtorConv::kVec3:
+            return "vec3";
+        case CtorConv::kVec4:
+            return "vec4";
+        case CtorConv::kMat2x2:
+            return "mat2x2";
+        case CtorConv::kMat2x3:
+            return "mat2x3";
+        case CtorConv::kMat2x4:
+            return "mat2x4";
+        case CtorConv::kMat3x2:
+            return "mat3x2";
+        case CtorConv::kMat3x3:
+            return "mat3x3";
+        case CtorConv::kMat3x4:
+            return "mat3x4";
+        case CtorConv::kMat4x2:
+            return "mat4x2";
+        case CtorConv::kMat4x3:
+            return "mat4x3";
+        case CtorConv::kMat4x4:
+            return "mat4x4";
+        case CtorConv::kPackedVec3:
+            return "packedVec3";
+    }
+    return "<unknown>";
+}
+
+}  // namespace tint::core::intrinsic
diff --git a/src/tint/lang/wgsl/resolver/ctor_conv_intrinsic.cc.tmpl b/src/tint/lang/core/intrinsic/ctor_conv.cc.tmpl
similarity index 76%
rename from src/tint/lang/wgsl/resolver/ctor_conv_intrinsic.cc.tmpl
rename to src/tint/lang/core/intrinsic/ctor_conv.cc.tmpl
index 46ffe81..960214c17 100644
--- a/src/tint/lang/wgsl/resolver/ctor_conv_intrinsic.cc.tmpl
+++ b/src/tint/lang/core/intrinsic/ctor_conv.cc.tmpl
@@ -13,16 +13,16 @@
 
 {{- $I := LoadIntrinsics "src/tint/lang/core/core.def" -}}
 
-#include "src/tint/lang/wgsl/resolver/ctor_conv_intrinsic.h"
+#include "src/tint/lang/core/intrinsic/ctor_conv.h"
 
-namespace tint::resolver {
+namespace tint::core::intrinsic {
 
-const char* str(CtorConvIntrinsic i) {
+const char* str(CtorConv i) {
     switch (i) {
-        case CtorConvIntrinsic::kNone:
+        case CtorConv::kNone:
             return "<none>";
 {{- range $I.Sem.ConstructorsAndConverters  }}
-        case CtorConvIntrinsic::k{{Title .Name}}:
+        case CtorConv::k{{Title .Name}}:
             return "{{.Name}}";
 {{- end  }}
     }
diff --git a/src/tint/lang/core/intrinsic/ctor_conv.h b/src/tint/lang/core/intrinsic/ctor_conv.h
new file mode 100644
index 0000000..3e7e762
--- /dev/null
+++ b/src/tint/lang/core/intrinsic/ctor_conv.h
@@ -0,0 +1,100 @@
+// Copyright 2021 The Tint Authors.
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//     http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+////////////////////////////////////////////////////////////////////////////////
+// File generated by tools/src/cmd/gen
+// using the template:
+//   src/tint/lang/core/intrinsic/ctor_conv.h.tmpl
+//
+// Do not modify this file directly
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef SRC_TINT_LANG_CORE_INTRINSIC_CTOR_CONV_H_
+#define SRC_TINT_LANG_CORE_INTRINSIC_CTOR_CONV_H_
+
+#include <cstdint>
+
+namespace tint::core::intrinsic {
+
+/// CtorConv is an enumerator of types that have a constructor or converter overload
+/// declared in the intrinsic table.
+enum class CtorConv {
+    kNone = -1,
+    kI32,
+    kU32,
+    kF32,
+    kF16,
+    kBool,
+    kVec2,
+    kVec3,
+    kVec4,
+    kMat2x2,
+    kMat2x3,
+    kMat2x4,
+    kMat3x2,
+    kMat3x3,
+    kMat3x4,
+    kMat4x2,
+    kMat4x3,
+    kMat4x4,
+    kPackedVec3,
+};
+
+/// @returns the name of the type.
+const char* str(CtorConv i);
+
+/// @param n the width of the vector
+/// @return the CtorConv for a vector of width `n`
+inline CtorConv VectorCtorConv(uint32_t n) {
+    switch (n) {
+        case 2:
+            return CtorConv::kVec2;
+        case 3:
+            return CtorConv::kVec3;
+        case 4:
+            return CtorConv::kVec4;
+    }
+    return CtorConv::kNone;
+}
+
+/// @param c the number of columns in the matrix
+/// @param r the number of rows in the matrix
+/// @return the CtorConv for a matrix with `c` columns and `r` rows
+inline CtorConv MatrixCtorConv(uint32_t c, uint32_t r) {
+    switch ((c - 2) * 3 + (r - 2)) {
+        case 0:
+            return CtorConv::kMat2x2;
+        case 1:
+            return CtorConv::kMat2x3;
+        case 2:
+            return CtorConv::kMat2x4;
+        case 3:
+            return CtorConv::kMat3x2;
+        case 4:
+            return CtorConv::kMat3x3;
+        case 5:
+            return CtorConv::kMat3x4;
+        case 6:
+            return CtorConv::kMat4x2;
+        case 7:
+            return CtorConv::kMat4x3;
+        case 8:
+            return CtorConv::kMat4x4;
+    }
+    return CtorConv::kNone;
+}
+
+}  // namespace tint::core::intrinsic
+
+#endif  // SRC_TINT_LANG_CORE_INTRINSIC_CTOR_CONV_H_
diff --git a/src/tint/lang/core/intrinsic/ctor_conv.h.tmpl b/src/tint/lang/core/intrinsic/ctor_conv.h.tmpl
new file mode 100644
index 0000000..b61ae9a
--- /dev/null
+++ b/src/tint/lang/core/intrinsic/ctor_conv.h.tmpl
@@ -0,0 +1,78 @@
+{{- /*
+--------------------------------------------------------------------------------
+Template file for use with tools/src/cmd/gen to generate ctor_conv_intrinsic.h
+
+To update the generated file, run:
+    ./tools/run gen
+
+See:
+* tools/src/cmd/gen for structures used by this template
+* https://golang.org/pkg/text/template/ for documentation on the template syntax
+--------------------------------------------------------------------------------
+*/ -}}
+
+{{- $I := LoadIntrinsics "src/tint/lang/core/core.def" -}}
+
+#ifndef SRC_TINT_LANG_CORE_INTRINSIC_CTOR_CONV_H_
+#define SRC_TINT_LANG_CORE_INTRINSIC_CTOR_CONV_H_
+
+#include <cstdint>
+
+namespace tint::core::intrinsic {
+
+/// CtorConv is an enumerator of types that have a constructor or converter overload
+/// declared in the intrinsic table.
+enum class CtorConv {
+    kNone = -1,
+{{- range $I.Sem.ConstructorsAndConverters }}
+    k{{Title .Name}},
+{{- end }}
+};
+
+/// @returns the name of the type.
+const char* str(CtorConv i);
+
+/// @param n the width of the vector
+/// @return the CtorConv for a vector of width `n`
+inline CtorConv VectorCtorConv(uint32_t n) {
+    switch (n) {
+        case 2:
+            return CtorConv::kVec2;
+        case 3:
+            return CtorConv::kVec3;
+        case 4:
+            return CtorConv::kVec4;
+    }
+    return CtorConv::kNone;
+}
+
+/// @param c the number of columns in the matrix
+/// @param r the number of rows in the matrix
+/// @return the CtorConv for a matrix with `c` columns and `r` rows
+inline CtorConv MatrixCtorConv(uint32_t c, uint32_t r) {
+    switch ((c - 2) * 3 + (r - 2)) {
+        case 0:
+            return CtorConv::kMat2x2;
+        case 1:
+            return CtorConv::kMat2x3;
+        case 2:
+            return CtorConv::kMat2x4;
+        case 3:
+            return CtorConv::kMat3x2;
+        case 4:
+            return CtorConv::kMat3x3;
+        case 5:
+            return CtorConv::kMat3x4;
+        case 6:
+            return CtorConv::kMat4x2;
+        case 7:
+            return CtorConv::kMat4x3;
+        case 8:
+            return CtorConv::kMat4x4;
+    }
+    return CtorConv::kNone;
+}
+
+}  // namespace tint::resolver
+
+#endif  // SRC_TINT_LANG_CORE_INTRINSIC_CTOR_CONV_H_
diff --git a/src/tint/lang/core/intrinsic/table.cc b/src/tint/lang/core/intrinsic/table.cc
index 437fef87..e16c598 100644
--- a/src/tint/lang/core/intrinsic/table.cc
+++ b/src/tint/lang/core/intrinsic/table.cc
@@ -973,7 +973,7 @@
                           const Source& source,
                           bool is_compound) override;
 
-    CtorOrConv Lookup(resolver::CtorConvIntrinsic type,
+    CtorOrConv Lookup(CtorConv type,
                       const type::Type* template_arg,
                       VectorRef<const type::Type*> args,
                       sem::EvaluationStage earliest_eval_stage,
@@ -1303,7 +1303,7 @@
     };
 }
 
-Table::CtorOrConv Impl::Lookup(resolver::CtorConvIntrinsic type,
+Table::CtorOrConv Impl::Lookup(CtorConv type,
                                const type::Type* template_arg,
                                VectorRef<const type::Type*> args,
                                sem::EvaluationStage earliest_eval_stage,
diff --git a/src/tint/lang/core/intrinsic/table.h b/src/tint/lang/core/intrinsic/table.h
index 8b10ead..55ac993 100644
--- a/src/tint/lang/core/intrinsic/table.h
+++ b/src/tint/lang/core/intrinsic/table.h
@@ -19,9 +19,9 @@
 #include <string>
 
 #include "src/tint/lang/core/constant/eval.h"
+#include "src/tint/lang/core/intrinsic/ctor_conv.h"
 #include "src/tint/lang/core/unary_op.h"
 #include "src/tint/lang/wgsl/ast/binary_expression.h"
-#include "src/tint/lang/wgsl/resolver/ctor_conv_intrinsic.h"
 #include "src/tint/lang/wgsl/sem/builtin.h"
 #include "src/tint/utils/containers/vector.h"
 
@@ -137,8 +137,7 @@
                                   const Source& source,
                                   bool is_compound) = 0;
 
-    /// Lookup looks for the value constructor or conversion overload for the given
-    /// CtorConvIntrinsic.
+    /// Lookup looks for the value constructor or conversion overload for the given CtorConv.
     /// @param type the type being constructed or converted
     /// @param template_arg the optional template argument
     /// @param args the argument types passed to the constructor / conversion call
@@ -150,7 +149,7 @@
     ///        after shader creation time (sem::EvaluationStage::kConstant).
     /// @param source the source of the call
     /// @return a sem::ValueConstructor, sem::ValueConversion or nullptr if nothing matched
-    virtual CtorOrConv Lookup(resolver::CtorConvIntrinsic type,
+    virtual CtorOrConv Lookup(CtorConv type,
                               const type::Type* template_arg,
                               VectorRef<const type::Type*> args,
                               sem::EvaluationStage earliest_eval_stage,
diff --git a/src/tint/lang/core/intrinsic/table_test.cc b/src/tint/lang/core/intrinsic/table_test.cc
index 7d5d665..7b1ac28 100644
--- a/src/tint/lang/core/intrinsic/table_test.cc
+++ b/src/tint/lang/core/intrinsic/table_test.cc
@@ -801,7 +801,7 @@
 TEST_F(IntrinsicTableTest, MatchTypeInitializerImplicit) {
     auto* i32 = create<type::I32>();
     auto* vec3_i32 = create<type::Vector>(i32, 3u);
-    auto result = table->Lookup(resolver::CtorConvIntrinsic::kVec3, nullptr, Vector{i32, i32, i32},
+    auto result = table->Lookup(CtorConv::kVec3, nullptr, Vector{i32, i32, i32},
                                 sem::EvaluationStage::kConstant, Source{{12, 34}});
     ASSERT_NE(result.target, nullptr);
     EXPECT_EQ(result.target->ReturnType(), vec3_i32);
@@ -816,7 +816,7 @@
 TEST_F(IntrinsicTableTest, MatchTypeInitializerExplicit) {
     auto* i32 = create<type::I32>();
     auto* vec3_i32 = create<type::Vector>(i32, 3u);
-    auto result = table->Lookup(resolver::CtorConvIntrinsic::kVec3, i32, Vector{i32, i32, i32},
+    auto result = table->Lookup(CtorConv::kVec3, i32, Vector{i32, i32, i32},
                                 sem::EvaluationStage::kConstant, Source{{12, 34}});
     ASSERT_NE(result.target, nullptr);
     EXPECT_EQ(result.target->ReturnType(), vec3_i32);
@@ -831,7 +831,7 @@
 TEST_F(IntrinsicTableTest, MismatchTypeInitializerImplicit) {
     auto* i32 = create<type::I32>();
     auto* f32 = create<type::F32>();
-    auto result = table->Lookup(resolver::CtorConvIntrinsic::kVec3, nullptr, Vector{i32, f32, i32},
+    auto result = table->Lookup(CtorConv::kVec3, nullptr, Vector{i32, f32, i32},
                                 sem::EvaluationStage::kConstant, Source{{12, 34}});
     ASSERT_EQ(result.target, nullptr);
     EXPECT_EQ(Diagnostics().str(),
@@ -858,7 +858,7 @@
 TEST_F(IntrinsicTableTest, MismatchTypeInitializerExplicit) {
     auto* i32 = create<type::I32>();
     auto* f32 = create<type::F32>();
-    auto result = table->Lookup(resolver::CtorConvIntrinsic::kVec3, i32, Vector{i32, f32, i32},
+    auto result = table->Lookup(CtorConv::kVec3, i32, Vector{i32, f32, i32},
                                 sem::EvaluationStage::kConstant, Source{{12, 34}});
     ASSERT_EQ(result.target, nullptr);
     EXPECT_EQ(Diagnostics().str(),
@@ -885,7 +885,7 @@
 TEST_F(IntrinsicTableTest, MatchTypeInitializerImplicitVecFromVecAbstract) {
     auto* ai = create<type::AbstractInt>();
     auto* vec3_ai = create<type::Vector>(ai, 3u);
-    auto result = table->Lookup(resolver::CtorConvIntrinsic::kVec3, nullptr, Vector{vec3_ai},
+    auto result = table->Lookup(CtorConv::kVec3, nullptr, Vector{vec3_ai},
                                 sem::EvaluationStage::kConstant, Source{{12, 34}});
     ASSERT_NE(result.target, nullptr);
     EXPECT_EQ(result.target->ReturnType(), vec3_ai);
@@ -900,9 +900,8 @@
     auto* vec2_ai = create<type::Vector>(create<type::AbstractInt>(), 2u);
     auto* vec2_af = create<type::Vector>(af, 2u);
     auto* mat2x2_af = create<type::Matrix>(vec2_af, 2u);
-    auto result =
-        table->Lookup(resolver::CtorConvIntrinsic::kMat2x2, nullptr, Vector{vec2_ai, vec2_ai},
-                      sem::EvaluationStage::kConstant, Source{{12, 34}});
+    auto result = table->Lookup(CtorConv::kMat2x2, nullptr, Vector{vec2_ai, vec2_ai},
+                                sem::EvaluationStage::kConstant, Source{{12, 34}});
     ASSERT_NE(result.target, nullptr);
     EXPECT_TYPE(result.target->ReturnType(), mat2x2_af);
     EXPECT_TRUE(result.target->Is<sem::ValueConstructor>());
@@ -915,7 +914,7 @@
 TEST_F(IntrinsicTableTest, MatchTypeInitializer_ConstantEval) {
     auto* ai = create<type::AbstractInt>();
     auto* vec3_ai = create<type::Vector>(ai, 3u);
-    auto result = table->Lookup(resolver::CtorConvIntrinsic::kVec3, nullptr, Vector{ai, ai, ai},
+    auto result = table->Lookup(CtorConv::kVec3, nullptr, Vector{ai, ai, ai},
                                 sem::EvaluationStage::kConstant, Source{{12, 34}});
     ASSERT_NE(result.target, nullptr);
     EXPECT_EQ(result.target->Stage(), sem::EvaluationStage::kConstant);
@@ -930,7 +929,7 @@
 
 TEST_F(IntrinsicTableTest, MatchTypeInitializer_RuntimeEval) {
     auto* ai = create<type::AbstractInt>();
-    auto result = table->Lookup(resolver::CtorConvIntrinsic::kVec3, nullptr, Vector{ai, ai, ai},
+    auto result = table->Lookup(CtorConv::kVec3, nullptr, Vector{ai, ai, ai},
                                 sem::EvaluationStage::kRuntime, Source{{12, 34}});
     auto* i32 = create<type::I32>();
     auto* vec3_i32 = create<type::Vector>(i32, 3u);
@@ -950,7 +949,7 @@
     auto* vec3_i32 = create<type::Vector>(i32, 3u);
     auto* f32 = create<type::F32>();
     auto* vec3_f32 = create<type::Vector>(f32, 3u);
-    auto result = table->Lookup(resolver::CtorConvIntrinsic::kVec3, i32, Vector{vec3_f32},
+    auto result = table->Lookup(CtorConv::kVec3, i32, Vector{vec3_f32},
                                 sem::EvaluationStage::kConstant, Source{{12, 34}});
     ASSERT_NE(result.target, nullptr);
     EXPECT_EQ(result.target->ReturnType(), vec3_i32);
@@ -963,8 +962,8 @@
     auto* arr =
         create<type::Array>(create<type::U32>(), create<type::RuntimeArrayCount>(), 4u, 4u, 4u, 4u);
     auto* f32 = create<type::F32>();
-    auto result = table->Lookup(resolver::CtorConvIntrinsic::kVec3, f32, Vector{arr},
-                                sem::EvaluationStage::kConstant, Source{{12, 34}});
+    auto result = table->Lookup(CtorConv::kVec3, f32, Vector{arr}, sem::EvaluationStage::kConstant,
+                                Source{{12, 34}});
     ASSERT_EQ(result.target, nullptr);
     EXPECT_EQ(Diagnostics().str(),
               R"(12:34 error: no matching constructor for vec3<f32>(array<u32>)
@@ -993,7 +992,7 @@
     auto* vec3_ai = create<type::Vector>(ai, 3u);
     auto* f32 = create<type::F32>();
     auto* vec3_f32 = create<type::Vector>(f32, 3u);
-    auto result = table->Lookup(resolver::CtorConvIntrinsic::kVec3, af, Vector{vec3_ai},
+    auto result = table->Lookup(CtorConv::kVec3, af, Vector{vec3_ai},
                                 sem::EvaluationStage::kConstant, Source{{12, 34}});
     ASSERT_NE(result.target, nullptr);
     EXPECT_EQ(result.target->Stage(), sem::EvaluationStage::kConstant);
@@ -1010,7 +1009,7 @@
     auto* vec3_ai = create<type::Vector>(ai, 3u);
     auto* vec3_f32 = create<type::Vector>(create<type::F32>(), 3u);
     auto* vec3_i32 = create<type::Vector>(create<type::I32>(), 3u);
-    auto result = table->Lookup(resolver::CtorConvIntrinsic::kVec3, af, Vector{vec3_ai},
+    auto result = table->Lookup(CtorConv::kVec3, af, Vector{vec3_ai},
                                 sem::EvaluationStage::kRuntime, Source{{12, 34}});
     ASSERT_NE(result.target, nullptr);
     EXPECT_EQ(result.target->Stage(), sem::EvaluationStage::kConstant);
@@ -1037,7 +1036,7 @@
     // The first should win overload resolution.
     auto* ai = create<type::AbstractInt>();
     auto* i32 = create<type::I32>();
-    auto result = table->Lookup(resolver::CtorConvIntrinsic::kI32, nullptr, Vector{ai},
+    auto result = table->Lookup(CtorConv::kI32, nullptr, Vector{ai},
                                 sem::EvaluationStage::kConstant, Source{});
     ASSERT_NE(result.target, nullptr);
     EXPECT_EQ(result.target->ReturnType(), i32);
diff --git a/src/tint/lang/wgsl/resolver/ctor_conv_intrinsic.cc b/src/tint/lang/wgsl/resolver/ctor_conv_intrinsic.cc
deleted file mode 100644
index 18a4b32..0000000
--- a/src/tint/lang/wgsl/resolver/ctor_conv_intrinsic.cc
+++ /dev/null
@@ -1,71 +0,0 @@
-// Copyright 2021 The Tint Authors.
-//
-// Licensed under the Apache License, Version 2.0 (the "License");
-// you may not use this file except in compliance with the License.
-// You may obtain a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-
-////////////////////////////////////////////////////////////////////////////////
-// File generated by tools/src/cmd/gen
-// using the template:
-//   src/tint/lang/wgsl/resolver/ctor_conv_intrinsic.cc.tmpl
-//
-// Do not modify this file directly
-////////////////////////////////////////////////////////////////////////////////
-
-#include "src/tint/lang/wgsl/resolver/ctor_conv_intrinsic.h"
-
-namespace tint::resolver {
-
-const char* str(CtorConvIntrinsic i) {
-    switch (i) {
-        case CtorConvIntrinsic::kNone:
-            return "<none>";
-        case CtorConvIntrinsic::kI32:
-            return "i32";
-        case CtorConvIntrinsic::kU32:
-            return "u32";
-        case CtorConvIntrinsic::kF32:
-            return "f32";
-        case CtorConvIntrinsic::kF16:
-            return "f16";
-        case CtorConvIntrinsic::kBool:
-            return "bool";
-        case CtorConvIntrinsic::kVec2:
-            return "vec2";
-        case CtorConvIntrinsic::kVec3:
-            return "vec3";
-        case CtorConvIntrinsic::kVec4:
-            return "vec4";
-        case CtorConvIntrinsic::kMat2x2:
-            return "mat2x2";
-        case CtorConvIntrinsic::kMat2x3:
-            return "mat2x3";
-        case CtorConvIntrinsic::kMat2x4:
-            return "mat2x4";
-        case CtorConvIntrinsic::kMat3x2:
-            return "mat3x2";
-        case CtorConvIntrinsic::kMat3x3:
-            return "mat3x3";
-        case CtorConvIntrinsic::kMat3x4:
-            return "mat3x4";
-        case CtorConvIntrinsic::kMat4x2:
-            return "mat4x2";
-        case CtorConvIntrinsic::kMat4x3:
-            return "mat4x3";
-        case CtorConvIntrinsic::kMat4x4:
-            return "mat4x4";
-        case CtorConvIntrinsic::kPackedVec3:
-            return "packedVec3";
-    }
-    return "<unknown>";
-}
-
-}  // namespace tint::resolver
diff --git a/src/tint/lang/wgsl/resolver/ctor_conv_intrinsic.h b/src/tint/lang/wgsl/resolver/ctor_conv_intrinsic.h
deleted file mode 100644
index 1c74a3c..0000000
--- a/src/tint/lang/wgsl/resolver/ctor_conv_intrinsic.h
+++ /dev/null
@@ -1,100 +0,0 @@
-// Copyright 2021 The Tint Authors.
-//
-// Licensed under the Apache License, Version 2.0 (the "License");
-// you may not use this file except in compliance with the License.
-// You may obtain a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-
-////////////////////////////////////////////////////////////////////////////////
-// File generated by tools/src/cmd/gen
-// using the template:
-//   src/tint/lang/wgsl/resolver/ctor_conv_intrinsic.h.tmpl
-//
-// Do not modify this file directly
-////////////////////////////////////////////////////////////////////////////////
-
-#ifndef SRC_TINT_LANG_WGSL_RESOLVER_CTOR_CONV_INTRINSIC_H_
-#define SRC_TINT_LANG_WGSL_RESOLVER_CTOR_CONV_INTRINSIC_H_
-
-#include <cstdint>
-
-namespace tint::resolver {
-
-/// CtorConvIntrinsic is an enumerator of types that have a constructor or converter overload
-/// declared in the intrinsic table.
-enum class CtorConvIntrinsic {
-    kNone = -1,
-    kI32,
-    kU32,
-    kF32,
-    kF16,
-    kBool,
-    kVec2,
-    kVec3,
-    kVec4,
-    kMat2x2,
-    kMat2x3,
-    kMat2x4,
-    kMat3x2,
-    kMat3x3,
-    kMat3x4,
-    kMat4x2,
-    kMat4x3,
-    kMat4x4,
-    kPackedVec3,
-};
-
-/// @returns the name of the type.
-const char* str(CtorConvIntrinsic i);
-
-/// @param n the width of the vector
-/// @return the CtorConvIntrinsic for a vector of width `n`
-inline CtorConvIntrinsic VectorCtorConvIntrinsic(uint32_t n) {
-    switch (n) {
-        case 2:
-            return CtorConvIntrinsic::kVec2;
-        case 3:
-            return CtorConvIntrinsic::kVec3;
-        case 4:
-            return CtorConvIntrinsic::kVec4;
-    }
-    return CtorConvIntrinsic::kNone;
-}
-
-/// @param c the number of columns in the matrix
-/// @param r the number of rows in the matrix
-/// @return the CtorConvIntrinsic for a matrix with `c` columns and `r` rows
-inline CtorConvIntrinsic MatrixCtorConvIntrinsic(uint32_t c, uint32_t r) {
-    switch ((c - 2) * 3 + (r - 2)) {
-        case 0:
-            return CtorConvIntrinsic::kMat2x2;
-        case 1:
-            return CtorConvIntrinsic::kMat2x3;
-        case 2:
-            return CtorConvIntrinsic::kMat2x4;
-        case 3:
-            return CtorConvIntrinsic::kMat3x2;
-        case 4:
-            return CtorConvIntrinsic::kMat3x3;
-        case 5:
-            return CtorConvIntrinsic::kMat3x4;
-        case 6:
-            return CtorConvIntrinsic::kMat4x2;
-        case 7:
-            return CtorConvIntrinsic::kMat4x3;
-        case 8:
-            return CtorConvIntrinsic::kMat4x4;
-    }
-    return CtorConvIntrinsic::kNone;
-}
-
-}  // namespace tint::resolver
-
-#endif  // SRC_TINT_LANG_WGSL_RESOLVER_CTOR_CONV_INTRINSIC_H_
diff --git a/src/tint/lang/wgsl/resolver/ctor_conv_intrinsic.h.tmpl b/src/tint/lang/wgsl/resolver/ctor_conv_intrinsic.h.tmpl
deleted file mode 100644
index 3a49828..0000000
--- a/src/tint/lang/wgsl/resolver/ctor_conv_intrinsic.h.tmpl
+++ /dev/null
@@ -1,78 +0,0 @@
-{{- /*
---------------------------------------------------------------------------------
-Template file for use with tools/src/cmd/gen to generate ctor_conv_intrinsic.h
-
-To update the generated file, run:
-    ./tools/run gen
-
-See:
-* tools/src/cmd/gen for structures used by this template
-* https://golang.org/pkg/text/template/ for documentation on the template syntax
---------------------------------------------------------------------------------
-*/ -}}
-
-{{- $I := LoadIntrinsics "src/tint/lang/core/core.def" -}}
-
-#ifndef SRC_TINT_LANG_WGSL_RESOLVER_CTOR_CONV_INTRINSIC_H_
-#define SRC_TINT_LANG_WGSL_RESOLVER_CTOR_CONV_INTRINSIC_H_
-
-#include <cstdint>
-
-namespace tint::resolver {
-
-/// CtorConvIntrinsic is an enumerator of types that have a constructor or converter overload
-/// declared in the intrinsic table.
-enum class CtorConvIntrinsic {
-    kNone = -1,
-{{- range $I.Sem.ConstructorsAndConverters }}
-    k{{Title .Name}},
-{{- end }}
-};
-
-/// @returns the name of the type.
-const char* str(CtorConvIntrinsic i);
-
-/// @param n the width of the vector
-/// @return the CtorConvIntrinsic for a vector of width `n`
-inline CtorConvIntrinsic VectorCtorConvIntrinsic(uint32_t n) {
-    switch (n) {
-        case 2:
-            return CtorConvIntrinsic::kVec2;
-        case 3:
-            return CtorConvIntrinsic::kVec3;
-        case 4:
-            return CtorConvIntrinsic::kVec4;
-    }
-    return CtorConvIntrinsic::kNone;
-}
-
-/// @param c the number of columns in the matrix
-/// @param r the number of rows in the matrix
-/// @return the CtorConvIntrinsic for a matrix with `c` columns and `r` rows
-inline CtorConvIntrinsic MatrixCtorConvIntrinsic(uint32_t c, uint32_t r) {
-    switch ((c - 2) * 3 + (r - 2)) {
-        case 0:
-            return CtorConvIntrinsic::kMat2x2;
-        case 1:
-            return CtorConvIntrinsic::kMat2x3;
-        case 2:
-            return CtorConvIntrinsic::kMat2x4;
-        case 3:
-            return CtorConvIntrinsic::kMat3x2;
-        case 4:
-            return CtorConvIntrinsic::kMat3x3;
-        case 5:
-            return CtorConvIntrinsic::kMat3x4;
-        case 6:
-            return CtorConvIntrinsic::kMat4x2;
-        case 7:
-            return CtorConvIntrinsic::kMat4x3;
-        case 8:
-            return CtorConvIntrinsic::kMat4x4;
-    }
-    return CtorConvIntrinsic::kNone;
-}
-
-}  // namespace tint::resolver
-
-#endif  // SRC_TINT_LANG_WGSL_RESOLVER_CTOR_CONV_INTRINSIC_H_
diff --git a/src/tint/lang/wgsl/resolver/resolver.cc b/src/tint/lang/wgsl/resolver/resolver.cc
index c258c28..17f0e1e 100644
--- a/src/tint/lang/wgsl/resolver/resolver.cc
+++ b/src/tint/lang/wgsl/resolver/resolver.cc
@@ -100,6 +100,8 @@
 namespace tint::resolver {
 namespace {
 
+using CtorConvIntrinsic = core::intrinsic::CtorConv;
+
 constexpr int64_t kMaxArrayElementCount = 65536;
 constexpr uint32_t kMaxStatementDepth = 127;
 constexpr size_t kMaxNestDepthOfCompositeType = 255;
@@ -2138,10 +2140,11 @@
                     TINT_ASSERT(v->Width() == 3u);
                     return ctor_or_conv(CtorConvIntrinsic::kPackedVec3, v->type());
                 }
-                return ctor_or_conv(VectorCtorConvIntrinsic(v->Width()), v->type());
+                return ctor_or_conv(core::intrinsic::VectorCtorConv(v->Width()), v->type());
             },
             [&](const type::Matrix* m) {
-                return ctor_or_conv(MatrixCtorConvIntrinsic(m->columns(), m->rows()), m->type());
+                return ctor_or_conv(core::intrinsic::MatrixCtorConv(m->columns(), m->rows()),
+                                    m->type());
             },
             [&](const type::Array* arr) -> sem::Call* {
                 auto* call_target = array_ctors_.GetOrCreate(