Move vector and matrix to type/.

This CL moves vector and matrix to type/ and updates the namespaces as
needed.

Bug: tint:1718
Change-Id: I48423b37f15cd69c03ab288143b2d36564789fbf
Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/113423
Reviewed-by: Ben Clayton <bclayton@google.com>
Kokoro: Kokoro <noreply+kokoro@google.com>
diff --git a/src/tint/BUILD.gn b/src/tint/BUILD.gn
index 01f36e2..23566b9 100644
--- a/src/tint/BUILD.gn
+++ b/src/tint/BUILD.gn
@@ -432,7 +432,6 @@
     "sem/info.h",
     "sem/loop_statement.h",
     "sem/materialize.h",
-    "sem/matrix.h",
     "sem/module.h",
     "sem/node.h",
     "sem/parameter_usage.h",
@@ -443,7 +442,6 @@
     "sem/type_conversion.h",
     "sem/type_initializer.h",
     "sem/type_mappings.h",
-    "sem/vector.h",
     "sem/while_statement.h",
     "source.cc",
     "source.h",
@@ -566,6 +564,7 @@
     "type/f16.h",
     "type/f32.h",
     "type/i32.h",
+    "type/matrix.h",
     "type/multisampled_texture.h",
     "type/node.h",
     "type/pointer.h",
@@ -578,6 +577,7 @@
     "type/type.h",
     "type/type_manager.h",
     "type/u32.h",
+    "type/vector.h",
     "type/void.h",
     "utils/bitcast.h",
     "utils/bitset.h",
@@ -670,8 +670,6 @@
     "sem/loop_statement.h",
     "sem/materialize.cc",
     "sem/materialize.h",
-    "sem/matrix.cc",
-    "sem/matrix.h",
     "sem/member_accessor_expression.cc",
     "sem/module.cc",
     "sem/module.h",
@@ -691,8 +689,6 @@
     "sem/type_initializer.h",
     "sem/type_mappings.h",
     "sem/variable.cc",
-    "sem/vector.cc",
-    "sem/vector.h",
     "sem/while_statement.cc",
     "sem/while_statement.h",
   ]
@@ -724,6 +720,8 @@
     "type/f32.h",
     "type/i32.cc",
     "type/i32.h",
+    "type/matrix.cc",
+    "type/matrix.h",
     "type/multisampled_texture.cc",
     "type/multisampled_texture.h",
     "type/node.cc",
@@ -748,6 +746,8 @@
     "type/type_manager.h",
     "type/u32.cc",
     "type/u32.h",
+    "type/vector.cc",
+    "type/vector.h",
     "type/void.cc",
     "type/void.h",
   ]
@@ -1207,9 +1207,7 @@
       "sem/atomic_test.cc",
       "sem/builtin_test.cc",
       "sem/expression_test.cc",
-      "sem/matrix_test.cc",
       "sem/struct_test.cc",
-      "sem/vector_test.cc",
     ]
   }
 
@@ -1222,6 +1220,7 @@
       "type/f16_test.cc",
       "type/f32_test.cc",
       "type/i32_test.cc",
+      "type/matrix_test.cc",
       "type/multisampled_texture_test.cc",
       "type/pointer_test.cc",
       "type/reference_test.cc",
@@ -1233,6 +1232,7 @@
       "type/type_manager_test.cc",
       "type/type_test.cc",
       "type/u32_test.cc",
+      "type/vector_test.cc",
     ]
   }
 
diff --git a/src/tint/CMakeLists.txt b/src/tint/CMakeLists.txt
index d691552..3d50b99 100644
--- a/src/tint/CMakeLists.txt
+++ b/src/tint/CMakeLists.txt
@@ -328,8 +328,6 @@
   sem/loop_statement.h
   sem/materialize.cc
   sem/materialize.h
-  sem/matrix.cc
-  sem/matrix.h
   sem/member_accessor_expression.cc
   sem/module.cc
   sem/module.h
@@ -347,8 +345,6 @@
   sem/type_conversion.h
   sem/type_mappings.h
   sem/variable.cc
-  sem/vector.cc
-  sem/vector.h
   sem/while_statement.cc
   sem/while_statement.h
   symbol_table.cc
@@ -481,6 +477,8 @@
   type/f32.h
   type/i32.cc
   type/i32.h
+  type/matrix.cc
+  type/matrix.h
   type/multisampled_texture.cc
   type/multisampled_texture.h
   type/node.cc
@@ -503,6 +501,8 @@
   type/type_manager.h
   type/u32.cc
   type/u32.h
+  type/vector.cc
+  type/vector.h
   type/void.cc
   type/void.h
   utils/bitcast.h
@@ -924,9 +924,7 @@
     sem/atomic.cc
     sem/builtin_test.cc
     sem/expression_test.cc
-    sem/matrix_test.cc
     sem/struct_test.cc
-    sem/vector_test.cc
     source_test.cc
     symbol_table_test.cc
     symbol_test.cc
@@ -941,6 +939,7 @@
     type/f16_test.cc
     type/f32_test.cc
     type/i32_test.cc
+    type/matrix_test.cc
     type/multisampled_texture_test.cc
     type/pointer_test.cc
     type/reference_test.cc
@@ -951,6 +950,7 @@
     type/type_test.cc
     type/type_manager_test.cc
     type/u32_test.cc
+    type/vector_test.cc
     utils/bitcast_test.cc
     utils/bitset_test.cc
     utils/block_allocator_test.cc
diff --git a/src/tint/inspector/inspector.cc b/src/tint/inspector/inspector.cc
index 8236a83..1b7a7fb 100644
--- a/src/tint/inspector/inspector.cc
+++ b/src/tint/inspector/inspector.cc
@@ -31,12 +31,10 @@
 #include "src/tint/sem/array.h"
 #include "src/tint/sem/call.h"
 #include "src/tint/sem/function.h"
-#include "src/tint/sem/matrix.h"
 #include "src/tint/sem/module.h"
 #include "src/tint/sem/statement.h"
 #include "src/tint/sem/struct.h"
 #include "src/tint/sem/variable.h"
-#include "src/tint/sem/vector.h"
 #include "src/tint/type/bool.h"
 #include "src/tint/type/depth_multisampled_texture.h"
 #include "src/tint/type/depth_texture.h"
@@ -44,10 +42,12 @@
 #include "src/tint/type/f16.h"
 #include "src/tint/type/f32.h"
 #include "src/tint/type/i32.h"
+#include "src/tint/type/matrix.h"
 #include "src/tint/type/multisampled_texture.h"
 #include "src/tint/type/sampled_texture.h"
 #include "src/tint/type/storage_texture.h"
 #include "src/tint/type/u32.h"
+#include "src/tint/type/vector.h"
 #include "src/tint/type/void.h"
 #include "src/tint/utils/math.h"
 #include "src/tint/utils/string.h"
@@ -86,7 +86,7 @@
         });
 
     CompositionType compositionType;
-    if (auto* vec = type->As<sem::Vector>()) {
+    if (auto* vec = type->As<type::Vector>()) {
         switch (vec->Width()) {
             case 2: {
                 compositionType = CompositionType::kVec2;
diff --git a/src/tint/inspector/resource_binding.cc b/src/tint/inspector/resource_binding.cc
index 6cbb4f1..b809e8e 100644
--- a/src/tint/inspector/resource_binding.cc
+++ b/src/tint/inspector/resource_binding.cc
@@ -15,12 +15,12 @@
 #include "src/tint/inspector/resource_binding.h"
 
 #include "src/tint/sem/array.h"
-#include "src/tint/sem/matrix.h"
-#include "src/tint/sem/vector.h"
 #include "src/tint/type/f32.h"
 #include "src/tint/type/i32.h"
+#include "src/tint/type/matrix.h"
 #include "src/tint/type/type.h"
 #include "src/tint/type/u32.h"
+#include "src/tint/type/vector.h"
 
 namespace tint::inspector {
 
@@ -52,9 +52,9 @@
 
     if (auto* at = base_type->As<sem::Array>()) {
         base_type = at->ElemType();
-    } else if (auto* mt = base_type->As<sem::Matrix>()) {
+    } else if (auto* mt = base_type->As<type::Matrix>()) {
         base_type = mt->type();
-    } else if (auto* vt = base_type->As<sem::Vector>()) {
+    } else if (auto* vt = base_type->As<type::Vector>()) {
         base_type = vt->type();
     }
 
diff --git a/src/tint/program_builder.h b/src/tint/program_builder.h
index 83cb18f..224c800 100644
--- a/src/tint/program_builder.h
+++ b/src/tint/program_builder.h
@@ -93,20 +93,20 @@
 #include "src/tint/sem/array.h"
 #include "src/tint/sem/array_count.h"
 #include "src/tint/sem/constant.h"
-#include "src/tint/sem/matrix.h"
 #include "src/tint/sem/struct.h"
-#include "src/tint/sem/vector.h"
 #include "src/tint/type/bool.h"
 #include "src/tint/type/depth_texture.h"
 #include "src/tint/type/external_texture.h"
 #include "src/tint/type/f16.h"
 #include "src/tint/type/f32.h"
 #include "src/tint/type/i32.h"
+#include "src/tint/type/matrix.h"
 #include "src/tint/type/multisampled_texture.h"
 #include "src/tint/type/pointer.h"
 #include "src/tint/type/sampled_texture.h"
 #include "src/tint/type/storage_texture.h"
 #include "src/tint/type/u32.h"
+#include "src/tint/type/vector.h"
 #include "src/tint/type/void.h"
 
 #ifdef CURRENTLY_IN_TINT_PUBLIC_HEADER
diff --git a/src/tint/resolver/array_accessor_test.cc b/src/tint/resolver/array_accessor_test.cc
index a41c00b..9c46789 100644
--- a/src/tint/resolver/array_accessor_test.cc
+++ b/src/tint/resolver/array_accessor_test.cc
@@ -111,8 +111,8 @@
     ASSERT_TRUE(TypeOf(acc)->Is<type::Reference>());
 
     auto* ref = TypeOf(acc)->As<type::Reference>();
-    ASSERT_TRUE(ref->StoreType()->Is<sem::Vector>());
-    EXPECT_EQ(ref->StoreType()->As<sem::Vector>()->Width(), 3u);
+    ASSERT_TRUE(ref->StoreType()->Is<type::Vector>());
+    EXPECT_EQ(ref->StoreType()->As<type::Vector>()->Width(), 3u);
 
     auto idx_sem = Sem().Get<sem::IndexAccessorExpression>(acc);
     ASSERT_NE(idx_sem, nullptr);
diff --git a/src/tint/resolver/builtin_test.cc b/src/tint/resolver/builtin_test.cc
index f8f2a68..955b945 100644
--- a/src/tint/resolver/builtin_test.cc
+++ b/src/tint/resolver/builtin_test.cc
@@ -117,9 +117,9 @@
     EXPECT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(expr), nullptr);
-    EXPECT_TRUE(TypeOf(expr)->Is<sem::Vector>());
-    EXPECT_EQ(TypeOf(expr)->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(TypeOf(expr)->As<sem::Vector>()->type()->Is<type::F32>());
+    EXPECT_TRUE(TypeOf(expr)->Is<type::Vector>());
+    EXPECT_EQ(TypeOf(expr)->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(TypeOf(expr)->As<type::Vector>()->type()->Is<type::F32>());
 }
 
 TEST_F(ResolverBuiltinTest, Select_Error_NoParams) {
@@ -315,9 +315,9 @@
 
         ASSERT_NE(TypeOf(call), nullptr);
         EXPECT_TRUE(TypeOf(call)->is_float_vector());
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-        ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-        EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::F32>());
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+        ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+        EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::F32>());
     } else {
         // Invalid parameter count.
         EXPECT_FALSE(r()->Resolve());
@@ -360,9 +360,9 @@
 
         ASSERT_NE(TypeOf(call), nullptr);
         EXPECT_TRUE(TypeOf(call)->is_float_vector());
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-        ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-        EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::F32>());
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+        ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+        EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::F32>());
     } else {
         // Invalid parameter count.
         EXPECT_FALSE(r()->Resolve());
@@ -406,9 +406,9 @@
 
         ASSERT_NE(TypeOf(call), nullptr);
         EXPECT_TRUE(TypeOf(call)->is_float_vector());
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-        ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-        EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::F32>());
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+        ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+        EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::F32>());
     } else {
         // Invalid parameter count.
         EXPECT_FALSE(r()->Resolve());
@@ -453,9 +453,9 @@
 
         ASSERT_NE(TypeOf(call), nullptr);
         EXPECT_TRUE(TypeOf(call)->is_float_vector());
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-        ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-        EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::F32>());
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+        ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+        EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::F32>());
     } else {
         // Invalid parameter count.
         EXPECT_FALSE(r()->Resolve());
@@ -511,9 +511,9 @@
 
         ASSERT_NE(TypeOf(call), nullptr);
         EXPECT_TRUE(TypeOf(call)->is_float_vector());
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-        ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-        EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::F16>());
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+        ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+        EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::F16>());
     } else {
         // Invalid parameter count.
         EXPECT_FALSE(r()->Resolve());
@@ -560,9 +560,9 @@
 
         ASSERT_NE(TypeOf(call), nullptr);
         EXPECT_TRUE(TypeOf(call)->is_float_vector());
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-        ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-        EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::F16>());
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+        ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+        EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::F16>());
     } else {
         // Invalid parameter count.
         EXPECT_FALSE(r()->Resolve());
@@ -610,9 +610,9 @@
 
         ASSERT_NE(TypeOf(call), nullptr);
         EXPECT_TRUE(TypeOf(call)->is_float_vector());
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-        ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-        EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::F16>());
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+        ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+        EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::F16>());
     } else {
         // Invalid parameter count.
         EXPECT_FALSE(r()->Resolve());
@@ -661,9 +661,9 @@
 
         ASSERT_NE(TypeOf(call), nullptr);
         EXPECT_TRUE(TypeOf(call)->is_float_vector());
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-        ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-        EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::F16>());
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+        ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+        EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::F16>());
     } else {
         // Invalid parameter count.
         EXPECT_FALSE(r()->Resolve());
@@ -738,8 +738,8 @@
 
     ASSERT_NE(TypeOf(call), nullptr);
     EXPECT_TRUE(TypeOf(call)->is_float_vector());
-    EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::F32>());
 }
 
 TEST_F(ResolverBuiltinFloatTest, Cross_f16) {
@@ -752,8 +752,8 @@
 
     ASSERT_NE(TypeOf(call), nullptr);
     EXPECT_TRUE(TypeOf(call)->is_float_vector());
-    EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::F16>());
+    EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::F16>());
 }
 
 TEST_F(ResolverBuiltinFloatTest, Cross_Error_NoArgs) {
@@ -989,18 +989,18 @@
     ASSERT_EQ(ty->Members().Length(), 2u);
 
     auto* fract = ty->Members()[0];
-    ASSERT_TRUE(fract->Type()->Is<sem::Vector>());
-    EXPECT_EQ(fract->Type()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(fract->Type()->As<sem::Vector>()->type()->Is<type::F32>());
+    ASSERT_TRUE(fract->Type()->Is<type::Vector>());
+    EXPECT_EQ(fract->Type()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(fract->Type()->As<type::Vector>()->type()->Is<type::F32>());
     EXPECT_EQ(fract->Offset(), 0u);
     EXPECT_EQ(fract->Size(), 12u);
     EXPECT_EQ(fract->Align(), 16u);
     EXPECT_EQ(fract->Name(), Sym("fract"));
 
     auto* exp = ty->Members()[1];
-    ASSERT_TRUE(exp->Type()->Is<sem::Vector>());
-    EXPECT_EQ(exp->Type()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(exp->Type()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(exp->Type()->Is<type::Vector>());
+    EXPECT_EQ(exp->Type()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(exp->Type()->As<type::Vector>()->type()->Is<type::I32>());
     EXPECT_EQ(exp->Offset(), 16u);
     EXPECT_EQ(exp->Size(), 12u);
     EXPECT_EQ(exp->Align(), 16u);
@@ -1024,18 +1024,18 @@
     ASSERT_EQ(ty->Members().Length(), 2u);
 
     auto* fract = ty->Members()[0];
-    ASSERT_TRUE(fract->Type()->Is<sem::Vector>());
-    EXPECT_EQ(fract->Type()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(fract->Type()->As<sem::Vector>()->type()->Is<type::F16>());
+    ASSERT_TRUE(fract->Type()->Is<type::Vector>());
+    EXPECT_EQ(fract->Type()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(fract->Type()->As<type::Vector>()->type()->Is<type::F16>());
     EXPECT_EQ(fract->Offset(), 0u);
     EXPECT_EQ(fract->Size(), 6u);
     EXPECT_EQ(fract->Align(), 8u);
     EXPECT_EQ(fract->Name(), Sym("fract"));
 
     auto* exp = ty->Members()[1];
-    ASSERT_TRUE(exp->Type()->Is<sem::Vector>());
-    EXPECT_EQ(exp->Type()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(exp->Type()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(exp->Type()->Is<type::Vector>());
+    EXPECT_EQ(exp->Type()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(exp->Type()->As<type::Vector>()->type()->Is<type::I32>());
     EXPECT_EQ(exp->Offset(), 16u);
     EXPECT_EQ(exp->Size(), 12u);
     EXPECT_EQ(exp->Align(), 16u);
@@ -1167,9 +1167,9 @@
 
     ASSERT_NE(TypeOf(call), nullptr);
     EXPECT_TRUE(TypeOf(call)->is_float_vector());
-    EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-    ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-    EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+    ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+    EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::F32>());
 }
 
 TEST_F(ResolverBuiltinFloatTest, Mix_VectorScalar_f16) {
@@ -1182,9 +1182,9 @@
 
     ASSERT_NE(TypeOf(call), nullptr);
     EXPECT_TRUE(TypeOf(call)->is_float_vector());
-    EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-    ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-    EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::F16>());
+    EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+    ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+    EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::F16>());
 }
 
 // modf: (f32) -> __modf_result, (vecN<f32>) -> __modf_result_vecN, (f16) -> __modf_result_f16,
@@ -1261,18 +1261,18 @@
     ASSERT_EQ(ty->Members().Length(), 2u);
 
     auto* fract = ty->Members()[0];
-    ASSERT_TRUE(fract->Type()->Is<sem::Vector>());
-    EXPECT_EQ(fract->Type()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(fract->Type()->As<sem::Vector>()->type()->Is<type::F32>());
+    ASSERT_TRUE(fract->Type()->Is<type::Vector>());
+    EXPECT_EQ(fract->Type()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(fract->Type()->As<type::Vector>()->type()->Is<type::F32>());
     EXPECT_EQ(fract->Offset(), 0u);
     EXPECT_EQ(fract->Size(), 12u);
     EXPECT_EQ(fract->Align(), 16u);
     EXPECT_EQ(fract->Name(), Sym("fract"));
 
     auto* whole = ty->Members()[1];
-    ASSERT_TRUE(whole->Type()->Is<sem::Vector>());
-    EXPECT_EQ(whole->Type()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(whole->Type()->As<sem::Vector>()->type()->Is<type::F32>());
+    ASSERT_TRUE(whole->Type()->Is<type::Vector>());
+    EXPECT_EQ(whole->Type()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(whole->Type()->As<type::Vector>()->type()->Is<type::F32>());
     EXPECT_EQ(whole->Offset(), 16u);
     EXPECT_EQ(whole->Size(), 12u);
     EXPECT_EQ(whole->Align(), 16u);
@@ -1296,18 +1296,18 @@
     ASSERT_EQ(ty->Members().Length(), 2u);
 
     auto* fract = ty->Members()[0];
-    ASSERT_TRUE(fract->Type()->Is<sem::Vector>());
-    EXPECT_EQ(fract->Type()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(fract->Type()->As<sem::Vector>()->type()->Is<type::F16>());
+    ASSERT_TRUE(fract->Type()->Is<type::Vector>());
+    EXPECT_EQ(fract->Type()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(fract->Type()->As<type::Vector>()->type()->Is<type::F16>());
     EXPECT_EQ(fract->Offset(), 0u);
     EXPECT_EQ(fract->Size(), 6u);
     EXPECT_EQ(fract->Align(), 8u);
     EXPECT_EQ(fract->Name(), Sym("fract"));
 
     auto* whole = ty->Members()[1];
-    ASSERT_TRUE(whole->Type()->Is<sem::Vector>());
-    EXPECT_EQ(whole->Type()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(whole->Type()->As<sem::Vector>()->type()->Is<type::F16>());
+    ASSERT_TRUE(whole->Type()->Is<type::Vector>());
+    EXPECT_EQ(whole->Type()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(whole->Type()->As<type::Vector>()->type()->Is<type::F16>());
     EXPECT_EQ(whole->Offset(), 8u);
     EXPECT_EQ(whole->Size(), 6u);
     EXPECT_EQ(whole->Align(), 8u);
@@ -1388,8 +1388,8 @@
 
     ASSERT_NE(TypeOf(call), nullptr);
     EXPECT_TRUE(TypeOf(call)->is_float_vector());
-    EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::F32>());
 }
 
 TEST_F(ResolverBuiltinFloatTest, Normalize_Vector_f16) {
@@ -1402,8 +1402,8 @@
 
     ASSERT_NE(TypeOf(call), nullptr);
     EXPECT_TRUE(TypeOf(call)->is_float_vector());
-    EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::F16>());
+    EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::F16>());
 }
 
 TEST_F(ResolverBuiltinFloatTest, Normalize_Error_NoParams) {
@@ -1486,9 +1486,9 @@
 
         ASSERT_NE(TypeOf(call), nullptr);
         EXPECT_TRUE(TypeOf(call)->is_signed_integer_vector());
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-        ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-        EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::I32>());
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+        ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+        EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::I32>());
     } else {
         // Invalid parameter count.
         EXPECT_FALSE(r()->Resolve());
@@ -1531,9 +1531,9 @@
 
         ASSERT_NE(TypeOf(call), nullptr);
         EXPECT_TRUE(TypeOf(call)->is_unsigned_integer_vector());
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-        ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-        EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::U32>());
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+        ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+        EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::U32>());
     } else {
         // Invalid parameter count.
         EXPECT_FALSE(r()->Resolve());
@@ -1576,9 +1576,9 @@
 
         ASSERT_NE(TypeOf(call), nullptr);
         EXPECT_TRUE(TypeOf(call)->is_signed_integer_vector());
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-        ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-        EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::I32>());
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+        ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+        EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::I32>());
     } else {
         // Invalid parameter count.
         EXPECT_FALSE(r()->Resolve());
@@ -1621,9 +1621,9 @@
 
         ASSERT_NE(TypeOf(call), nullptr);
         EXPECT_TRUE(TypeOf(call)->is_unsigned_integer_vector());
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-        ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-        EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::U32>());
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+        ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+        EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::U32>());
     } else {
         // Invalid parameter count.
         EXPECT_FALSE(r()->Resolve());
@@ -1667,9 +1667,9 @@
 
         ASSERT_NE(TypeOf(call), nullptr);
         EXPECT_TRUE(TypeOf(call)->is_signed_integer_vector());
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-        ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-        EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::I32>());
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+        ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+        EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::I32>());
     } else {
         // Invalid parameter count.
         EXPECT_FALSE(r()->Resolve());
@@ -1714,9 +1714,9 @@
 
         ASSERT_NE(TypeOf(call), nullptr);
         EXPECT_TRUE(TypeOf(call)->is_unsigned_integer_vector());
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-        ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-        EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::U32>());
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+        ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+        EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::U32>());
     } else {
         // Invalid parameter count.
         EXPECT_FALSE(r()->Resolve());
@@ -1761,9 +1761,9 @@
 
         ASSERT_NE(TypeOf(call), nullptr);
         EXPECT_TRUE(TypeOf(call)->is_signed_integer_vector());
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-        ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-        EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::I32>());
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+        ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+        EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::I32>());
     } else {
         // Invalid parameter count.
         EXPECT_FALSE(r()->Resolve());
@@ -1808,9 +1808,9 @@
 
         ASSERT_NE(TypeOf(call), nullptr);
         EXPECT_TRUE(TypeOf(call)->is_unsigned_integer_vector());
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 3u);
-        ASSERT_NE(TypeOf(call)->As<sem::Vector>()->type(), nullptr);
-        EXPECT_TRUE(TypeOf(call)->As<sem::Vector>()->type()->Is<type::U32>());
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 3u);
+        ASSERT_NE(TypeOf(call)->As<type::Vector>()->type(), nullptr);
+        EXPECT_TRUE(TypeOf(call)->As<type::Vector>()->type()->Is<type::U32>());
     } else {
         // Invalid parameter count.
         EXPECT_FALSE(r()->Resolve());
@@ -2053,9 +2053,9 @@
     EXPECT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(expr), nullptr);
-    ASSERT_TRUE(TypeOf(expr)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(expr)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(expr)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(expr)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(expr)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(expr)->As<type::Vector>()->Width(), 4u);
 }
 
 TEST_P(ResolverBuiltinDerivativeTest, MissingParam) {
@@ -2180,15 +2180,15 @@
     EXPECT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(expr), nullptr);
-    ASSERT_TRUE(TypeOf(expr)->Is<sem::Vector>());
+    ASSERT_TRUE(TypeOf(expr)->Is<type::Vector>());
     if (type == Texture::kF32) {
-        EXPECT_TRUE(TypeOf(expr)->As<sem::Vector>()->type()->Is<type::F32>());
+        EXPECT_TRUE(TypeOf(expr)->As<type::Vector>()->type()->Is<type::F32>());
     } else if (type == Texture::kI32) {
-        EXPECT_TRUE(TypeOf(expr)->As<sem::Vector>()->type()->Is<type::I32>());
+        EXPECT_TRUE(TypeOf(expr)->As<type::Vector>()->type()->Is<type::I32>());
     } else {
-        EXPECT_TRUE(TypeOf(expr)->As<sem::Vector>()->type()->Is<type::U32>());
+        EXPECT_TRUE(TypeOf(expr)->As<type::Vector>()->type()->Is<type::U32>());
     }
-    EXPECT_EQ(TypeOf(expr)->As<sem::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(expr)->As<type::Vector>()->Width(), 4u);
 }
 
 INSTANTIATE_TEST_SUITE_P(ResolverTest,
@@ -2476,14 +2476,14 @@
             case ast::TextureDimension::k2dArray:
             case ast::TextureDimension::kCube:
             case ast::TextureDimension::kCubeArray: {
-                auto* vec = As<sem::Vector>(TypeOf(call));
+                auto* vec = As<type::Vector>(TypeOf(call));
                 ASSERT_NE(vec, nullptr);
                 EXPECT_EQ(vec->Width(), 2u);
                 EXPECT_TRUE(vec->type()->Is<type::U32>());
                 break;
             }
             case ast::TextureDimension::k3d: {
-                auto* vec = As<sem::Vector>(TypeOf(call));
+                auto* vec = As<type::Vector>(TypeOf(call));
                 ASSERT_NE(vec, nullptr);
                 EXPECT_EQ(vec->Width(), 3u);
                 EXPECT_TRUE(vec->type()->Is<type::U32>());
@@ -2499,7 +2499,7 @@
     } else if (std::string(param.function) == "textureStore") {
         EXPECT_TRUE(TypeOf(call)->Is<type::Void>());
     } else if (std::string(param.function) == "textureGather") {
-        auto* vec = As<sem::Vector>(TypeOf(call));
+        auto* vec = As<type::Vector>(TypeOf(call));
         ASSERT_NE(vec, nullptr);
         EXPECT_EQ(vec->Width(), 4u);
         switch (param.texture_data_type) {
@@ -2514,7 +2514,7 @@
                 break;
         }
     } else if (std::string(param.function) == "textureGatherCompare") {
-        auto* vec = As<sem::Vector>(TypeOf(call));
+        auto* vec = As<type::Vector>(TypeOf(call));
         ASSERT_NE(vec, nullptr);
         EXPECT_EQ(vec->Width(), 4u);
         EXPECT_TRUE(vec->type()->Is<type::F32>());
@@ -2523,7 +2523,7 @@
             case ast::builtin::test::TextureKind::kRegular:
             case ast::builtin::test::TextureKind::kMultisampled:
             case ast::builtin::test::TextureKind::kStorage: {
-                auto* vec = TypeOf(call)->As<sem::Vector>();
+                auto* vec = TypeOf(call)->As<type::Vector>();
                 ASSERT_NE(vec, nullptr);
                 switch (param.texture_data_type) {
                     case ast::builtin::test::TextureDataType::kF32:
@@ -2646,9 +2646,9 @@
     ASSERT_NE(TypeOf(call), nullptr);
     EXPECT_TRUE(TypeOf(call)->is_float_vector());
     if (pack4) {
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 4u);
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 4u);
     } else {
-        EXPECT_EQ(TypeOf(call)->As<sem::Vector>()->Width(), 2u);
+        EXPECT_EQ(TypeOf(call)->As<type::Vector>()->Width(), 2u);
     }
 }
 
diff --git a/src/tint/resolver/builtins_validation_test.cc b/src/tint/resolver/builtins_validation_test.cc
index 9616627..b6fdddb 100644
--- a/src/tint/resolver/builtins_validation_test.cc
+++ b/src/tint/resolver/builtins_validation_test.cc
@@ -907,12 +907,12 @@
     ASSERT_TRUE(res_ty != nullptr);
     auto members = res_ty->Members();
     ASSERT_EQ(members.Length(), 2u);
-    ASSERT_TRUE(members[0]->Type()->Is<sem::Vector>());
-    ASSERT_TRUE(members[1]->Type()->Is<sem::Vector>());
-    EXPECT_EQ(members[0]->Type()->As<sem::Vector>()->Width(), 2u);
-    EXPECT_TRUE(members[0]->Type()->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(members[1]->Type()->As<sem::Vector>()->Width(), 2u);
-    EXPECT_TRUE(members[1]->Type()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(members[0]->Type()->Is<type::Vector>());
+    ASSERT_TRUE(members[1]->Type()->Is<type::Vector>());
+    EXPECT_EQ(members[0]->Type()->As<type::Vector>()->Width(), 2u);
+    EXPECT_TRUE(members[0]->Type()->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(members[1]->Type()->As<type::Vector>()->Width(), 2u);
+    EXPECT_TRUE(members[1]->Type()->As<type::Vector>()->type()->Is<type::I32>());
 }
 
 TEST_F(ResolverBuiltinsValidationTest, Frexp_Vec3) {
@@ -924,12 +924,12 @@
     ASSERT_TRUE(res_ty != nullptr);
     auto members = res_ty->Members();
     ASSERT_EQ(members.Length(), 2u);
-    ASSERT_TRUE(members[0]->Type()->Is<sem::Vector>());
-    ASSERT_TRUE(members[1]->Type()->Is<sem::Vector>());
-    EXPECT_EQ(members[0]->Type()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(members[0]->Type()->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(members[1]->Type()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(members[1]->Type()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(members[0]->Type()->Is<type::Vector>());
+    ASSERT_TRUE(members[1]->Type()->Is<type::Vector>());
+    EXPECT_EQ(members[0]->Type()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(members[0]->Type()->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(members[1]->Type()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(members[1]->Type()->As<type::Vector>()->type()->Is<type::I32>());
 }
 
 TEST_F(ResolverBuiltinsValidationTest, Frexp_Vec4) {
@@ -941,12 +941,12 @@
     ASSERT_TRUE(res_ty != nullptr);
     auto members = res_ty->Members();
     ASSERT_EQ(members.Length(), 2u);
-    ASSERT_TRUE(members[0]->Type()->Is<sem::Vector>());
-    ASSERT_TRUE(members[1]->Type()->Is<sem::Vector>());
-    EXPECT_EQ(members[0]->Type()->As<sem::Vector>()->Width(), 4u);
-    EXPECT_TRUE(members[0]->Type()->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(members[1]->Type()->As<sem::Vector>()->Width(), 4u);
-    EXPECT_TRUE(members[1]->Type()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(members[0]->Type()->Is<type::Vector>());
+    ASSERT_TRUE(members[1]->Type()->Is<type::Vector>());
+    EXPECT_EQ(members[0]->Type()->As<type::Vector>()->Width(), 4u);
+    EXPECT_TRUE(members[0]->Type()->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(members[1]->Type()->As<type::Vector>()->Width(), 4u);
+    EXPECT_TRUE(members[1]->Type()->As<type::Vector>()->type()->Is<type::I32>());
 }
 
 TEST_F(ResolverBuiltinsValidationTest, Modf_Scalar) {
@@ -971,12 +971,12 @@
     ASSERT_TRUE(res_ty != nullptr);
     auto members = res_ty->Members();
     ASSERT_EQ(members.Length(), 2u);
-    ASSERT_TRUE(members[0]->Type()->Is<sem::Vector>());
-    ASSERT_TRUE(members[1]->Type()->Is<sem::Vector>());
-    EXPECT_EQ(members[0]->Type()->As<sem::Vector>()->Width(), 2u);
-    EXPECT_TRUE(members[0]->Type()->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(members[1]->Type()->As<sem::Vector>()->Width(), 2u);
-    EXPECT_TRUE(members[1]->Type()->As<sem::Vector>()->type()->Is<type::F32>());
+    ASSERT_TRUE(members[0]->Type()->Is<type::Vector>());
+    ASSERT_TRUE(members[1]->Type()->Is<type::Vector>());
+    EXPECT_EQ(members[0]->Type()->As<type::Vector>()->Width(), 2u);
+    EXPECT_TRUE(members[0]->Type()->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(members[1]->Type()->As<type::Vector>()->Width(), 2u);
+    EXPECT_TRUE(members[1]->Type()->As<type::Vector>()->type()->Is<type::F32>());
 }
 
 TEST_F(ResolverBuiltinsValidationTest, Modf_Vec3) {
@@ -988,12 +988,12 @@
     ASSERT_TRUE(res_ty != nullptr);
     auto members = res_ty->Members();
     ASSERT_EQ(members.Length(), 2u);
-    ASSERT_TRUE(members[0]->Type()->Is<sem::Vector>());
-    ASSERT_TRUE(members[1]->Type()->Is<sem::Vector>());
-    EXPECT_EQ(members[0]->Type()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(members[0]->Type()->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(members[1]->Type()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(members[1]->Type()->As<sem::Vector>()->type()->Is<type::F32>());
+    ASSERT_TRUE(members[0]->Type()->Is<type::Vector>());
+    ASSERT_TRUE(members[1]->Type()->Is<type::Vector>());
+    EXPECT_EQ(members[0]->Type()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(members[0]->Type()->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(members[1]->Type()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(members[1]->Type()->As<type::Vector>()->type()->Is<type::F32>());
 }
 
 TEST_F(ResolverBuiltinsValidationTest, Modf_Vec4) {
@@ -1005,12 +1005,12 @@
     ASSERT_TRUE(res_ty != nullptr);
     auto members = res_ty->Members();
     ASSERT_EQ(members.Length(), 2u);
-    ASSERT_TRUE(members[0]->Type()->Is<sem::Vector>());
-    ASSERT_TRUE(members[1]->Type()->Is<sem::Vector>());
-    EXPECT_EQ(members[0]->Type()->As<sem::Vector>()->Width(), 4u);
-    EXPECT_TRUE(members[0]->Type()->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(members[1]->Type()->As<sem::Vector>()->Width(), 4u);
-    EXPECT_TRUE(members[1]->Type()->As<sem::Vector>()->type()->Is<type::F32>());
+    ASSERT_TRUE(members[0]->Type()->Is<type::Vector>());
+    ASSERT_TRUE(members[1]->Type()->Is<type::Vector>());
+    EXPECT_EQ(members[0]->Type()->As<type::Vector>()->Width(), 4u);
+    EXPECT_TRUE(members[0]->Type()->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(members[1]->Type()->As<type::Vector>()->Width(), 4u);
+    EXPECT_TRUE(members[1]->Type()->As<type::Vector>()->type()->Is<type::F32>());
 }
 
 TEST_F(ResolverBuiltinsValidationTest, Cross_Float_Vec3) {
diff --git a/src/tint/resolver/const_eval.cc b/src/tint/resolver/const_eval.cc
index 682e0a3..28cb619 100644
--- a/src/tint/resolver/const_eval.cc
+++ b/src/tint/resolver/const_eval.cc
@@ -25,17 +25,17 @@
 #include "src/tint/program_builder.h"
 #include "src/tint/sem/array.h"
 #include "src/tint/sem/constant.h"
-#include "src/tint/sem/matrix.h"
 #include "src/tint/sem/member_accessor_expression.h"
 #include "src/tint/sem/type_initializer.h"
-#include "src/tint/sem/vector.h"
 #include "src/tint/type/abstract_float.h"
 #include "src/tint/type/abstract_int.h"
 #include "src/tint/type/bool.h"
 #include "src/tint/type/f16.h"
 #include "src/tint/type/f32.h"
 #include "src/tint/type/i32.h"
+#include "src/tint/type/matrix.h"
 #include "src/tint/type/u32.h"
+#include "src/tint/type/vector.h"
 #include "src/tint/utils/bitcast.h"
 #include "src/tint/utils/compiler_macros.h"
 #include "src/tint/utils/map.h"
@@ -477,11 +477,11 @@
 const ImplConstant* ZeroValue(ProgramBuilder& builder, const type::Type* type) {
     return Switch(
         type,  //
-        [&](const sem::Vector* v) -> const ImplConstant* {
+        [&](const type::Vector* v) -> const ImplConstant* {
             auto* zero_el = ZeroValue(builder, v->type());
             return builder.create<Splat>(type, zero_el, v->Width());
         },
-        [&](const sem::Matrix* m) -> const ImplConstant* {
+        [&](const type::Matrix* m) -> const ImplConstant* {
             auto* zero_el = ZeroValue(builder, m->ColumnType());
             return builder.create<Splat>(type, zero_el, m->columns());
         },
@@ -530,7 +530,7 @@
     }
     return Switch(
         a->Type(),  //
-        [&](const sem::Vector* vec) {
+        [&](const type::Vector* vec) {
             for (size_t i = 0; i < vec->Width(); i++) {
                 if (!Equal(a->Index(i), b->Index(i))) {
                     return false;
@@ -538,7 +538,7 @@
             }
             return true;
         },
-        [&](const sem::Matrix* mat) {
+        [&](const type::Matrix* mat) {
             for (size_t i = 0; i < mat->columns(); i++) {
                 if (!Equal(a->Index(i), b->Index(i))) {
                     return false;
@@ -1181,7 +1181,7 @@
 ConstEval::Result ConstEval::Dot(const Source& source,
                                  const sem::Constant* v1,
                                  const sem::Constant* v2) {
-    auto* vec_ty = v1->Type()->As<sem::Vector>();
+    auto* vec_ty = v1->Type()->As<type::Vector>();
     TINT_ASSERT(Resolver, vec_ty);
     auto* elem_ty = vec_ty->type();
     switch (vec_ty->Width()) {
@@ -1208,7 +1208,7 @@
 ConstEval::Result ConstEval::Length(const Source& source,
                                     const type::Type* ty,
                                     const sem::Constant* c0) {
-    auto* vec_ty = c0->Type()->As<sem::Vector>();
+    auto* vec_ty = c0->Type()->As<type::Vector>();
     // Evaluates to the absolute value of e if T is scalar.
     if (vec_ty == nullptr) {
         auto create = [&](auto e) {
@@ -1358,7 +1358,7 @@
                                       utils::VectorRef<const sem::Constant*> args,
                                       const Source&) {
     if (auto* arg = args[0]) {
-        return builder.create<Splat>(ty, arg, static_cast<const sem::Vector*>(ty)->Width());
+        return builder.create<Splat>(ty, arg, static_cast<const type::Vector*>(ty)->Width());
     }
     return nullptr;
 }
@@ -1379,7 +1379,7 @@
             return nullptr;
         }
         auto* arg_ty = arg->Type();
-        if (auto* arg_vec = arg_ty->As<sem::Vector>()) {
+        if (auto* arg_vec = arg_ty->As<type::Vector>()) {
             // Extract out vector elements.
             for (uint32_t j = 0; j < arg_vec->Width(); j++) {
                 auto* el = val->Index(j);
@@ -1398,7 +1398,7 @@
 ConstEval::Result ConstEval::MatInitS(const type::Type* ty,
                                       utils::VectorRef<const sem::Constant*> args,
                                       const Source&) {
-    auto* m = static_cast<const sem::Matrix*>(ty);
+    auto* m = static_cast<const type::Matrix*>(ty);
 
     utils::Vector<const sem::Constant*, 4> els;
     for (uint32_t c = 0; c < m->columns(); c++) {
@@ -1550,8 +1550,8 @@
 ConstEval::Result ConstEval::OpMultiplyMatVec(const type::Type* ty,
                                               utils::VectorRef<const sem::Constant*> args,
                                               const Source& source) {
-    auto* mat_ty = args[0]->Type()->As<sem::Matrix>();
-    auto* vec_ty = args[1]->Type()->As<sem::Vector>();
+    auto* mat_ty = args[0]->Type()->As<type::Matrix>();
+    auto* vec_ty = args[1]->Type()->As<type::Vector>();
     auto* elem_ty = vec_ty->type();
 
     auto dot = [&](const sem::Constant* m, size_t row, const sem::Constant* v) {
@@ -1600,8 +1600,8 @@
 ConstEval::Result ConstEval::OpMultiplyVecMat(const type::Type* ty,
                                               utils::VectorRef<const sem::Constant*> args,
                                               const Source& source) {
-    auto* vec_ty = args[0]->Type()->As<sem::Vector>();
-    auto* mat_ty = args[1]->Type()->As<sem::Matrix>();
+    auto* vec_ty = args[0]->Type()->As<type::Vector>();
+    auto* mat_ty = args[1]->Type()->As<type::Matrix>();
     auto* elem_ty = vec_ty->type();
 
     auto dot = [&](const sem::Constant* v, const sem::Constant* m, size_t col) {
@@ -1653,8 +1653,8 @@
                                               const Source& source) {
     auto* mat1 = args[0];
     auto* mat2 = args[1];
-    auto* mat1_ty = mat1->Type()->As<sem::Matrix>();
-    auto* mat2_ty = mat2->Type()->As<sem::Matrix>();
+    auto* mat1_ty = mat1->Type()->As<type::Matrix>();
+    auto* mat2_ty = mat2->Type()->As<type::Matrix>();
     auto* elem_ty = mat1_ty->type();
 
     auto dot = [&](const sem::Constant* m1, size_t row, const sem::Constant* m2, size_t col) {
@@ -1706,7 +1706,7 @@
         }
 
         // Add column vector to matrix
-        auto* col_vec_ty = ty->As<sem::Matrix>()->ColumnType();
+        auto* col_vec_ty = ty->As<type::Matrix>()->ColumnType();
         result_mat.Push(CreateComposite(builder, col_vec_ty, col_vec));
     }
     return CreateComposite(builder, ty, result_mat);
@@ -2283,7 +2283,7 @@
                                    const Source& source) {
     auto* u = args[0];
     auto* v = args[1];
-    auto* elem_ty = u->Type()->As<sem::Vector>()->type();
+    auto* elem_ty = u->Type()->As<type::Vector>()->type();
 
     // cross product of a v3 is the determinant of the 3x3 matrix:
     //
@@ -2352,7 +2352,7 @@
                                          const Source& source) {
     auto calculate = [&]() -> ConstEval::Result {
         auto* m = args[0];
-        auto* mat_ty = m->Type()->As<sem::Matrix>();
+        auto* mat_ty = m->Type()->As<type::Matrix>();
         auto me = [&](size_t r, size_t c) { return m->Index(c)->Index(r); };
         switch (mat_ty->rows()) {
             case 2:
@@ -2674,7 +2674,7 @@
             });
     };
 
-    if (auto* vec = arg->Type()->As<sem::Vector>()) {
+    if (auto* vec = arg->Type()->As<type::Vector>()) {
         utils::Vector<const sem::Constant*, 4> fract_els;
         utils::Vector<const sem::Constant*, 4> exp_els;
         for (uint32_t i = 0; i < vec->Width(); i++) {
@@ -2685,8 +2685,8 @@
             fract_els.Push(fe.fract.Get());
             exp_els.Push(fe.exp.Get());
         }
-        auto fract_ty = builder.create<sem::Vector>(fract_els[0]->Type(), vec->Width());
-        auto exp_ty = builder.create<sem::Vector>(exp_els[0]->Type(), vec->Width());
+        auto fract_ty = builder.create<type::Vector>(fract_els[0]->Type(), vec->Width());
+        auto exp_ty = builder.create<type::Vector>(exp_els[0]->Type(), vec->Width());
         return CreateComposite(builder, ty,
                                utils::Vector<const sem::Constant*, 2>{
                                    CreateComposite(builder, fract_ty, std::move(fract_els)),
@@ -3044,7 +3044,7 @@
         // e1 - 2 * dot(e2, e1) * e2.
         auto* e1 = args[0];
         auto* e2 = args[1];
-        auto* vec_ty = ty->As<sem::Vector>();
+        auto* vec_ty = ty->As<type::Vector>();
         auto* el_ty = vec_ty->type();
 
         // dot(e2, e1)
@@ -3082,7 +3082,7 @@
 ConstEval::Result ConstEval::refract(const type::Type* ty,
                                      utils::VectorRef<const sem::Constant*> args,
                                      const Source& source) {
-    auto* vec_ty = ty->As<sem::Vector>();
+    auto* vec_ty = ty->As<type::Vector>();
     auto* el_ty = vec_ty->type();
 
     auto compute_k = [&](auto e3, auto dot_e2_e1) -> ConstEval::Result {
@@ -3436,9 +3436,9 @@
                                        utils::VectorRef<const sem::Constant*> args,
                                        const Source&) {
     auto* m = args[0];
-    auto* mat_ty = m->Type()->As<sem::Matrix>();
+    auto* mat_ty = m->Type()->As<type::Matrix>();
     auto me = [&](size_t r, size_t c) { return m->Index(c)->Index(r); };
-    auto* result_mat_ty = ty->As<sem::Matrix>();
+    auto* result_mat_ty = ty->As<type::Matrix>();
 
     // Produce column vectors from each row
     utils::Vector<const sem::Constant*, 4> result_mat;
diff --git a/src/tint/resolver/const_eval_construction_test.cc b/src/tint/resolver/const_eval_construction_test.cc
index bf9cb62..30aef8a 100644
--- a/src/tint/resolver/const_eval_construction_test.cc
+++ b/src/tint/resolver/const_eval_construction_test.cc
@@ -110,7 +110,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::I32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -143,7 +143,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::U32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -176,7 +176,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -211,7 +211,7 @@
 
     auto* sem = Sem().Get(expr);
     EXPECT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F16>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -244,7 +244,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::Bool>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -277,7 +277,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::I32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -310,7 +310,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::U32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -343,7 +343,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -378,7 +378,7 @@
 
     auto* sem = Sem().Get(expr);
     EXPECT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F16>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -412,7 +412,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::Bool>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -445,7 +445,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::I32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -478,7 +478,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::U32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -511,7 +511,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -546,7 +546,7 @@
 
     auto* sem = Sem().Get(expr);
     EXPECT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F16>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -579,7 +579,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::Bool>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -612,7 +612,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::I32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -645,7 +645,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::U32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -678,7 +678,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -711,7 +711,7 @@
 
     auto* sem = Sem().Get(expr);
     EXPECT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -744,7 +744,7 @@
 
     auto* sem = Sem().Get(expr);
     EXPECT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -777,7 +777,7 @@
 
     auto* sem = Sem().Get(expr);
     EXPECT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -810,7 +810,7 @@
 
     auto* sem = Sem().Get(expr);
     EXPECT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -845,7 +845,7 @@
 
     auto* sem = Sem().Get(expr);
     EXPECT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F16>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -880,7 +880,7 @@
 
     auto* sem = Sem().Get(expr);
     EXPECT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F16>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -915,7 +915,7 @@
 
     auto* sem = Sem().Get(expr);
     EXPECT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F16>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -950,7 +950,7 @@
 
     auto* sem = Sem().Get(expr);
     EXPECT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F16>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -985,7 +985,7 @@
 
     auto* sem = Sem().Get(expr);
     EXPECT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F16>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -1018,7 +1018,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::Bool>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -1051,7 +1051,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::Bool>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -1084,7 +1084,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::Bool>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -1117,7 +1117,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* mat = sem->Type()->As<sem::Matrix>();
+    auto* mat = sem->Type()->As<type::Matrix>();
     ASSERT_NE(mat, nullptr);
     EXPECT_TRUE(mat->type()->Is<type::F32>());
     EXPECT_EQ(mat->columns(), 2u);
@@ -1168,7 +1168,7 @@
 
     auto* sem = Sem().Get(expr);
     EXPECT_NE(sem, nullptr);
-    auto* mat = sem->Type()->As<sem::Matrix>();
+    auto* mat = sem->Type()->As<type::Matrix>();
     ASSERT_NE(mat, nullptr);
     EXPECT_TRUE(mat->type()->Is<type::F16>());
     EXPECT_EQ(mat->columns(), 2u);
@@ -1217,7 +1217,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* mat = sem->Type()->As<sem::Matrix>();
+    auto* mat = sem->Type()->As<type::Matrix>();
     ASSERT_NE(mat, nullptr);
     EXPECT_TRUE(mat->type()->Is<type::F32>());
     EXPECT_EQ(mat->columns(), 3u);
@@ -1269,7 +1269,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* mat = sem->Type()->As<sem::Matrix>();
+    auto* mat = sem->Type()->As<type::Matrix>();
     ASSERT_NE(mat, nullptr);
     EXPECT_TRUE(mat->type()->Is<type::F32>());
     EXPECT_EQ(mat->columns(), 3u);
@@ -1394,7 +1394,7 @@
     ASSERT_NE(sem, nullptr);
     auto* arr = sem->Type()->As<sem::Array>();
     ASSERT_NE(arr, nullptr);
-    EXPECT_TRUE(arr->ElemType()->Is<sem::Vector>());
+    EXPECT_TRUE(arr->ElemType()->Is<type::Vector>());
     EXPECT_TYPE(sem->ConstantValue()->Type(), sem->Type());
     EXPECT_TRUE(sem->ConstantValue()->AllEqual());
     EXPECT_TRUE(sem->ConstantValue()->AnyZero());
@@ -1557,7 +1557,7 @@
     ASSERT_NE(sem, nullptr);
     auto* arr = sem->Type()->As<sem::Array>();
     ASSERT_NE(arr, nullptr);
-    EXPECT_TRUE(arr->ElemType()->Is<sem::Vector>());
+    EXPECT_TRUE(arr->ElemType()->Is<type::Vector>());
     EXPECT_TYPE(sem->ConstantValue()->Type(), sem->Type());
     EXPECT_FALSE(sem->ConstantValue()->AllEqual());
     EXPECT_FALSE(sem->ConstantValue()->AnyZero());
@@ -1733,8 +1733,9 @@
     EXPECT_TRUE(sem->ConstantValue()->Index(0)->AllEqual());
     EXPECT_TRUE(sem->ConstantValue()->Index(0)->AnyZero());
     EXPECT_TRUE(sem->ConstantValue()->Index(0)->AllZero());
-    EXPECT_TRUE(sem->ConstantValue()->Index(0)->Type()->Is<sem::Vector>());
-    EXPECT_TRUE(sem->ConstantValue()->Index(0)->Type()->As<sem::Vector>()->type()->Is<type::F32>());
+    EXPECT_TRUE(sem->ConstantValue()->Index(0)->Type()->Is<type::Vector>());
+    EXPECT_TRUE(
+        sem->ConstantValue()->Index(0)->Type()->As<type::Vector>()->type()->Is<type::F32>());
     EXPECT_EQ(sem->ConstantValue()->Index(0)->Index(0)->As<f32>(), 0._f);
     EXPECT_EQ(sem->ConstantValue()->Index(0)->Index(1)->As<f32>(), 0._f);
     EXPECT_EQ(sem->ConstantValue()->Index(0)->Index(2)->As<f32>(), 0._f);
@@ -1742,8 +1743,9 @@
     EXPECT_TRUE(sem->ConstantValue()->Index(1)->AllEqual());
     EXPECT_TRUE(sem->ConstantValue()->Index(1)->AnyZero());
     EXPECT_TRUE(sem->ConstantValue()->Index(1)->AllZero());
-    EXPECT_TRUE(sem->ConstantValue()->Index(1)->Type()->Is<sem::Vector>());
-    EXPECT_TRUE(sem->ConstantValue()->Index(1)->Type()->As<sem::Vector>()->type()->Is<type::F32>());
+    EXPECT_TRUE(sem->ConstantValue()->Index(1)->Type()->Is<type::Vector>());
+    EXPECT_TRUE(
+        sem->ConstantValue()->Index(1)->Type()->As<type::Vector>()->type()->Is<type::F32>());
     EXPECT_EQ(sem->ConstantValue()->Index(1)->Index(0)->As<f32>(), 0._f);
     EXPECT_EQ(sem->ConstantValue()->Index(1)->Index(1)->As<f32>(), 0._f);
     EXPECT_EQ(sem->ConstantValue()->Index(1)->Index(2)->As<f32>(), 0._f);
@@ -1751,8 +1753,9 @@
     EXPECT_TRUE(sem->ConstantValue()->Index(2)->AllEqual());
     EXPECT_TRUE(sem->ConstantValue()->Index(2)->AnyZero());
     EXPECT_TRUE(sem->ConstantValue()->Index(2)->AllZero());
-    EXPECT_TRUE(sem->ConstantValue()->Index(2)->Type()->Is<sem::Vector>());
-    EXPECT_TRUE(sem->ConstantValue()->Index(2)->Type()->As<sem::Vector>()->type()->Is<type::F32>());
+    EXPECT_TRUE(sem->ConstantValue()->Index(2)->Type()->Is<type::Vector>());
+    EXPECT_TRUE(
+        sem->ConstantValue()->Index(2)->Type()->As<type::Vector>()->type()->Is<type::F32>());
     EXPECT_EQ(sem->ConstantValue()->Index(2)->Index(0)->As<f32>(), 0._f);
     EXPECT_EQ(sem->ConstantValue()->Index(2)->Index(1)->As<f32>(), 0._f);
     EXPECT_EQ(sem->ConstantValue()->Index(2)->Index(2)->As<f32>(), 0._f);
@@ -1787,16 +1790,18 @@
     EXPECT_TRUE(sem->ConstantValue()->Index(0)->AllEqual());
     EXPECT_TRUE(sem->ConstantValue()->Index(0)->AnyZero());
     EXPECT_TRUE(sem->ConstantValue()->Index(0)->AllZero());
-    EXPECT_TRUE(sem->ConstantValue()->Index(0)->Type()->Is<sem::Vector>());
-    EXPECT_TRUE(sem->ConstantValue()->Index(0)->Type()->As<sem::Vector>()->type()->Is<type::I32>());
+    EXPECT_TRUE(sem->ConstantValue()->Index(0)->Type()->Is<type::Vector>());
+    EXPECT_TRUE(
+        sem->ConstantValue()->Index(0)->Type()->As<type::Vector>()->type()->Is<type::I32>());
     EXPECT_EQ(sem->ConstantValue()->Index(0)->Index(0)->As<i32>(), 0_i);
     EXPECT_EQ(sem->ConstantValue()->Index(0)->Index(1)->As<i32>(), 0_i);
 
     EXPECT_TRUE(sem->ConstantValue()->Index(1)->AllEqual());
     EXPECT_TRUE(sem->ConstantValue()->Index(1)->AnyZero());
     EXPECT_TRUE(sem->ConstantValue()->Index(1)->AllZero());
-    EXPECT_TRUE(sem->ConstantValue()->Index(1)->Type()->Is<sem::Vector>());
-    EXPECT_TRUE(sem->ConstantValue()->Index(1)->Type()->As<sem::Vector>()->type()->Is<type::U32>());
+    EXPECT_TRUE(sem->ConstantValue()->Index(1)->Type()->Is<type::Vector>());
+    EXPECT_TRUE(
+        sem->ConstantValue()->Index(1)->Type()->As<type::Vector>()->type()->Is<type::U32>());
     EXPECT_EQ(sem->ConstantValue()->Index(1)->Index(0)->As<u32>(), 0_u);
     EXPECT_EQ(sem->ConstantValue()->Index(1)->Index(1)->As<u32>(), 0_u);
     EXPECT_EQ(sem->ConstantValue()->Index(1)->Index(2)->As<u32>(), 0_u);
@@ -1804,8 +1809,9 @@
     EXPECT_TRUE(sem->ConstantValue()->Index(2)->AllEqual());
     EXPECT_TRUE(sem->ConstantValue()->Index(2)->AnyZero());
     EXPECT_TRUE(sem->ConstantValue()->Index(2)->AllZero());
-    EXPECT_TRUE(sem->ConstantValue()->Index(2)->Type()->Is<sem::Vector>());
-    EXPECT_TRUE(sem->ConstantValue()->Index(2)->Type()->As<sem::Vector>()->type()->Is<type::F32>());
+    EXPECT_TRUE(sem->ConstantValue()->Index(2)->Type()->Is<type::Vector>());
+    EXPECT_TRUE(
+        sem->ConstantValue()->Index(2)->Type()->As<type::Vector>()->type()->Is<type::F32>());
     EXPECT_EQ(sem->ConstantValue()->Index(2)->Index(0)->As<f32>(), 0._f);
     EXPECT_EQ(sem->ConstantValue()->Index(2)->Index(1)->As<f32>(), 0._f);
     EXPECT_EQ(sem->ConstantValue()->Index(2)->Index(2)->As<f32>(), 0._f);
@@ -1814,8 +1820,9 @@
     EXPECT_TRUE(sem->ConstantValue()->Index(3)->AllEqual());
     EXPECT_TRUE(sem->ConstantValue()->Index(3)->AnyZero());
     EXPECT_TRUE(sem->ConstantValue()->Index(3)->AllZero());
-    EXPECT_TRUE(sem->ConstantValue()->Index(3)->Type()->Is<sem::Vector>());
-    EXPECT_TRUE(sem->ConstantValue()->Index(3)->Type()->As<sem::Vector>()->type()->Is<type::F16>());
+    EXPECT_TRUE(sem->ConstantValue()->Index(3)->Type()->Is<type::Vector>());
+    EXPECT_TRUE(
+        sem->ConstantValue()->Index(3)->Type()->As<type::Vector>()->type()->Is<type::F16>());
     EXPECT_EQ(sem->ConstantValue()->Index(3)->Index(0)->As<f16>(), 0._h);
     EXPECT_EQ(sem->ConstantValue()->Index(3)->Index(1)->As<f16>(), 0._h);
     EXPECT_EQ(sem->ConstantValue()->Index(3)->Index(2)->As<f16>(), 0._h);
@@ -1823,9 +1830,9 @@
     EXPECT_TRUE(sem->ConstantValue()->Index(4)->AllEqual());
     EXPECT_TRUE(sem->ConstantValue()->Index(4)->AnyZero());
     EXPECT_TRUE(sem->ConstantValue()->Index(4)->AllZero());
-    EXPECT_TRUE(sem->ConstantValue()->Index(4)->Type()->Is<sem::Vector>());
+    EXPECT_TRUE(sem->ConstantValue()->Index(4)->Type()->Is<type::Vector>());
     EXPECT_TRUE(
-        sem->ConstantValue()->Index(4)->Type()->As<sem::Vector>()->type()->Is<type::Bool>());
+        sem->ConstantValue()->Index(4)->Type()->As<type::Vector>()->type()->Is<type::Bool>());
     EXPECT_EQ(sem->ConstantValue()->Index(4)->Index(0)->As<bool>(), false);
     EXPECT_EQ(sem->ConstantValue()->Index(4)->Index(1)->As<bool>(), false);
 }
@@ -1961,16 +1968,18 @@
     EXPECT_TRUE(sem->ConstantValue()->Index(0)->AllEqual());
     EXPECT_FALSE(sem->ConstantValue()->Index(0)->AnyZero());
     EXPECT_FALSE(sem->ConstantValue()->Index(0)->AllZero());
-    EXPECT_TRUE(sem->ConstantValue()->Index(0)->Type()->Is<sem::Vector>());
-    EXPECT_TRUE(sem->ConstantValue()->Index(0)->Type()->As<sem::Vector>()->type()->Is<type::I32>());
+    EXPECT_TRUE(sem->ConstantValue()->Index(0)->Type()->Is<type::Vector>());
+    EXPECT_TRUE(
+        sem->ConstantValue()->Index(0)->Type()->As<type::Vector>()->type()->Is<type::I32>());
     EXPECT_EQ(sem->ConstantValue()->Index(0)->Index(0)->As<i32>(), 1_i);
     EXPECT_EQ(sem->ConstantValue()->Index(0)->Index(1)->As<i32>(), 1_i);
 
     EXPECT_TRUE(sem->ConstantValue()->Index(1)->AllEqual());
     EXPECT_FALSE(sem->ConstantValue()->Index(1)->AnyZero());
     EXPECT_FALSE(sem->ConstantValue()->Index(1)->AllZero());
-    EXPECT_TRUE(sem->ConstantValue()->Index(1)->Type()->Is<sem::Vector>());
-    EXPECT_TRUE(sem->ConstantValue()->Index(1)->Type()->As<sem::Vector>()->type()->Is<type::U32>());
+    EXPECT_TRUE(sem->ConstantValue()->Index(1)->Type()->Is<type::Vector>());
+    EXPECT_TRUE(
+        sem->ConstantValue()->Index(1)->Type()->As<type::Vector>()->type()->Is<type::U32>());
     EXPECT_EQ(sem->ConstantValue()->Index(1)->Index(0)->As<u32>(), 2_u);
     EXPECT_EQ(sem->ConstantValue()->Index(1)->Index(1)->As<u32>(), 2_u);
     EXPECT_EQ(sem->ConstantValue()->Index(1)->Index(2)->As<u32>(), 2_u);
@@ -1978,8 +1987,9 @@
     EXPECT_TRUE(sem->ConstantValue()->Index(2)->AllEqual());
     EXPECT_FALSE(sem->ConstantValue()->Index(2)->AnyZero());
     EXPECT_FALSE(sem->ConstantValue()->Index(2)->AllZero());
-    EXPECT_TRUE(sem->ConstantValue()->Index(2)->Type()->Is<sem::Vector>());
-    EXPECT_TRUE(sem->ConstantValue()->Index(2)->Type()->As<sem::Vector>()->type()->Is<type::F32>());
+    EXPECT_TRUE(sem->ConstantValue()->Index(2)->Type()->Is<type::Vector>());
+    EXPECT_TRUE(
+        sem->ConstantValue()->Index(2)->Type()->As<type::Vector>()->type()->Is<type::F32>());
     EXPECT_EQ(sem->ConstantValue()->Index(2)->Index(0)->As<f32>(), 3._f);
     EXPECT_EQ(sem->ConstantValue()->Index(2)->Index(1)->As<f32>(), 3._f);
     EXPECT_EQ(sem->ConstantValue()->Index(2)->Index(2)->As<f32>(), 3._f);
@@ -1988,8 +1998,9 @@
     EXPECT_TRUE(sem->ConstantValue()->Index(3)->AllEqual());
     EXPECT_FALSE(sem->ConstantValue()->Index(3)->AnyZero());
     EXPECT_FALSE(sem->ConstantValue()->Index(3)->AllZero());
-    EXPECT_TRUE(sem->ConstantValue()->Index(3)->Type()->Is<sem::Vector>());
-    EXPECT_TRUE(sem->ConstantValue()->Index(3)->Type()->As<sem::Vector>()->type()->Is<type::F16>());
+    EXPECT_TRUE(sem->ConstantValue()->Index(3)->Type()->Is<type::Vector>());
+    EXPECT_TRUE(
+        sem->ConstantValue()->Index(3)->Type()->As<type::Vector>()->type()->Is<type::F16>());
     EXPECT_EQ(sem->ConstantValue()->Index(3)->Index(0)->As<f16>(), 4._h);
     EXPECT_EQ(sem->ConstantValue()->Index(3)->Index(1)->As<f16>(), 4._h);
     EXPECT_EQ(sem->ConstantValue()->Index(3)->Index(2)->As<f16>(), 4._h);
@@ -1997,9 +2008,9 @@
     EXPECT_TRUE(sem->ConstantValue()->Index(4)->AllEqual());
     EXPECT_TRUE(sem->ConstantValue()->Index(4)->AnyZero());
     EXPECT_TRUE(sem->ConstantValue()->Index(4)->AllZero());
-    EXPECT_TRUE(sem->ConstantValue()->Index(4)->Type()->Is<sem::Vector>());
+    EXPECT_TRUE(sem->ConstantValue()->Index(4)->Type()->Is<type::Vector>());
     EXPECT_TRUE(
-        sem->ConstantValue()->Index(4)->Type()->As<sem::Vector>()->type()->Is<type::Bool>());
+        sem->ConstantValue()->Index(4)->Type()->As<type::Vector>()->type()->Is<type::Bool>());
     EXPECT_EQ(sem->ConstantValue()->Index(4)->Index(0)->As<bool>(), false);
     EXPECT_EQ(sem->ConstantValue()->Index(4)->Index(1)->As<bool>(), false);
 }
diff --git a/src/tint/resolver/const_eval_conversion_test.cc b/src/tint/resolver/const_eval_conversion_test.cc
index 7b277b6..435c4e6 100644
--- a/src/tint/resolver/const_eval_conversion_test.cc
+++ b/src/tint/resolver/const_eval_conversion_test.cc
@@ -79,7 +79,7 @@
 
     auto* target_sem_ty = type.sem(*this);
     if (kind == Kind::kVector) {
-        target_sem_ty = create<sem::Vector>(target_sem_ty, 3u);
+        target_sem_ty = create<type::Vector>(target_sem_ty, 3u);
     }
 
     if (unrepresentable) {
@@ -230,7 +230,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::I32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -263,7 +263,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -298,7 +298,7 @@
 
     auto* sem = Sem().Get(expr);
     EXPECT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::I32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -333,7 +333,7 @@
 
     auto* sem = Sem().Get(expr);
     EXPECT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F16>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -366,7 +366,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::I32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -399,7 +399,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::U32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -444,7 +444,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F16>());
     EXPECT_EQ(vec->Width(), 3u);
diff --git a/src/tint/resolver/const_eval_indexing_test.cc b/src/tint/resolver/const_eval_indexing_test.cc
index 723e758..c894d8f 100644
--- a/src/tint/resolver/const_eval_indexing_test.cc
+++ b/src/tint/resolver/const_eval_indexing_test.cc
@@ -75,7 +75,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_EQ(vec->Width(), 2u);
     EXPECT_TYPE(sem->ConstantValue()->Type(), sem->Type());
@@ -117,7 +117,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_EQ(vec->Width(), 2u);
     EXPECT_TYPE(sem->ConstantValue()->Type(), sem->Type());
@@ -163,7 +163,7 @@
 
     auto* sem = Sem().Get(expr);
     ASSERT_NE(sem, nullptr);
-    auto* vec = sem->Type()->As<sem::Vector>();
+    auto* vec = sem->Type()->As<type::Vector>();
     ASSERT_NE(vec, nullptr);
     EXPECT_TRUE(vec->type()->Is<type::F32>());
     EXPECT_EQ(vec->Width(), 3u);
@@ -232,9 +232,9 @@
     {
         auto* mat = Sem().Get(mat_expr);
         EXPECT_NE(mat, nullptr);
-        auto* ty = mat->Type()->As<sem::Matrix>();
+        auto* ty = mat->Type()->As<type::Matrix>();
         ASSERT_NE(mat->Type(), nullptr);
-        EXPECT_TRUE(ty->ColumnType()->Is<sem::Vector>());
+        EXPECT_TRUE(ty->ColumnType()->Is<type::Vector>());
         EXPECT_EQ(ty->columns(), 2u);
         EXPECT_EQ(ty->rows(), 3u);
         EXPECT_EQ(mat->ConstantValue()->Type(), mat->Type());
@@ -275,7 +275,7 @@
     {
         auto* vec = Sem().Get(vec_expr);
         EXPECT_NE(vec, nullptr);
-        auto* ty = vec->Type()->As<sem::Vector>();
+        auto* ty = vec->Type()->As<type::Vector>();
         ASSERT_NE(vec->Type(), nullptr);
         EXPECT_TRUE(ty->type()->Is<type::F32>());
         EXPECT_EQ(ty->Width(), 3u);
diff --git a/src/tint/resolver/const_eval_member_access_test.cc b/src/tint/resolver/const_eval_member_access_test.cc
index 3fb8fc3..1dcd3a7 100644
--- a/src/tint/resolver/const_eval_member_access_test.cc
+++ b/src/tint/resolver/const_eval_member_access_test.cc
@@ -79,10 +79,10 @@
 
     auto* sem = Sem().Get(c);
     ASSERT_NE(sem, nullptr);
-    EXPECT_TRUE(sem->Type()->Is<sem::Matrix>());
+    EXPECT_TRUE(sem->Type()->Is<type::Matrix>());
     auto* cv = sem->ConstantValue();
     EXPECT_TYPE(cv->Type(), sem->Type());
-    EXPECT_TRUE(cv->Index(0)->Type()->Is<sem::Vector>());
+    EXPECT_TRUE(cv->Index(0)->Type()->Is<type::Vector>());
     EXPECT_TRUE(cv->Index(0)->Index(0)->Type()->Is<type::AbstractFloat>());
     EXPECT_FALSE(cv->AllEqual());
     EXPECT_FALSE(cv->AnyZero());
diff --git a/src/tint/resolver/intrinsic_table.cc b/src/tint/resolver/intrinsic_table.cc
index 660845d..4ce974f 100644
--- a/src/tint/resolver/intrinsic_table.cc
+++ b/src/tint/resolver/intrinsic_table.cc
@@ -413,7 +413,7 @@
         return true;
     }
 
-    if (auto* v = ty->As<sem::Vector>()) {
+    if (auto* v = ty->As<type::Vector>()) {
         N = v->Width();
         T = v->type();
         return true;
@@ -428,7 +428,7 @@
         return true;
     }
 
-    if (auto* v = ty->As<sem::Vector>()) {
+    if (auto* v = ty->As<type::Vector>()) {
         if (v->Width() == N) {
             T = v->type();
             return true;
@@ -437,13 +437,13 @@
     return false;
 }
 
-const sem::Vector* build_vec(MatchState& state, Number N, const type::Type* el) {
-    return state.builder.create<sem::Vector>(el, N.Value());
+const type::Vector* build_vec(MatchState& state, Number N, const type::Type* el) {
+    return state.builder.create<type::Vector>(el, N.Value());
 }
 
 template <uint32_t N>
-const sem::Vector* build_vec(MatchState& state, const type::Type* el) {
-    return state.builder.create<sem::Vector>(el, N);
+const type::Vector* build_vec(MatchState& state, const type::Type* el) {
+    return state.builder.create<type::Vector>(el, N);
 }
 
 constexpr auto match_vec2 = match_vec<2>;
@@ -461,7 +461,7 @@
         T = ty;
         return true;
     }
-    if (auto* m = ty->As<sem::Matrix>()) {
+    if (auto* m = ty->As<type::Matrix>()) {
         M = m->columns();
         N = m->ColumnType()->Width();
         T = m->type();
@@ -476,7 +476,7 @@
         T = ty;
         return true;
     }
-    if (auto* m = ty->As<sem::Matrix>()) {
+    if (auto* m = ty->As<type::Matrix>()) {
         if (m->columns() == C && m->rows() == R) {
             T = m->type();
             return true;
@@ -485,15 +485,15 @@
     return false;
 }
 
-const sem::Matrix* build_mat(MatchState& state, Number C, Number R, const type::Type* T) {
-    auto* column_type = state.builder.create<sem::Vector>(T, R.Value());
-    return state.builder.create<sem::Matrix>(column_type, C.Value());
+const type::Matrix* build_mat(MatchState& state, Number C, Number R, const type::Type* T) {
+    auto* column_type = state.builder.create<type::Vector>(T, R.Value());
+    return state.builder.create<type::Matrix>(column_type, C.Value());
 }
 
 template <uint32_t C, uint32_t R>
-const sem::Matrix* build_mat(MatchState& state, const type::Type* T) {
-    auto* column_type = state.builder.create<sem::Vector>(T, R);
-    return state.builder.create<sem::Matrix>(column_type, C);
+const type::Matrix* build_mat(MatchState& state, const type::Type* T) {
+    auto* column_type = state.builder.create<type::Vector>(T, R);
+    return state.builder.create<type::Matrix>(column_type, C);
 }
 
 constexpr auto build_mat2x2 = build_mat<2, 2>;
@@ -862,11 +862,13 @@
 const sem::Struct* build_modf_result_vec(MatchState& state, Number& n, const type::Type* el) {
     auto prefix = "__modf_result_vec" + std::to_string(n.Value());
     auto build_f32 = [&] {
-        auto* vec = state.builder.create<sem::Vector>(state.builder.create<type::F32>(), n.Value());
+        auto* vec =
+            state.builder.create<type::Vector>(state.builder.create<type::F32>(), n.Value());
         return build_struct(state.builder, prefix + "_f32", {{"fract", vec}, {"whole", vec}});
     };
     auto build_f16 = [&] {
-        auto* vec = state.builder.create<sem::Vector>(state.builder.create<type::F16>(), n.Value());
+        auto* vec =
+            state.builder.create<type::Vector>(state.builder.create<type::F16>(), n.Value());
         return build_struct(state.builder, prefix + "_f16", {{"fract", vec}, {"whole", vec}});
     };
 
@@ -875,7 +877,7 @@
         [&](const type::F32*) { return build_f32(); },  //
         [&](const type::F16*) { return build_f16(); },  //
         [&](const type::AbstractFloat*) {
-            auto* vec = state.builder.create<sem::Vector>(el, n.Value());
+            auto* vec = state.builder.create<type::Vector>(el, n.Value());
             auto* abstract =
                 build_struct(state.builder, prefix + "_abstract", {{"fract", vec}, {"whole", vec}});
             abstract->SetConcreteTypes(utils::Vector{build_f32(), build_f16()});
@@ -921,13 +923,13 @@
 const sem::Struct* build_frexp_result_vec(MatchState& state, Number& n, const type::Type* el) {
     auto prefix = "__frexp_result_vec" + std::to_string(n.Value());
     auto build_f32 = [&] {
-        auto* f = state.builder.create<sem::Vector>(state.builder.create<type::F32>(), n.Value());
-        auto* e = state.builder.create<sem::Vector>(state.builder.create<type::I32>(), n.Value());
+        auto* f = state.builder.create<type::Vector>(state.builder.create<type::F32>(), n.Value());
+        auto* e = state.builder.create<type::Vector>(state.builder.create<type::I32>(), n.Value());
         return build_struct(state.builder, prefix + "_f32", {{"fract", f}, {"exp", e}});
     };
     auto build_f16 = [&] {
-        auto* f = state.builder.create<sem::Vector>(state.builder.create<type::F16>(), n.Value());
-        auto* e = state.builder.create<sem::Vector>(state.builder.create<type::I32>(), n.Value());
+        auto* f = state.builder.create<type::Vector>(state.builder.create<type::F16>(), n.Value());
+        auto* e = state.builder.create<type::Vector>(state.builder.create<type::I32>(), n.Value());
         return build_struct(state.builder, prefix + "_f16", {{"fract", f}, {"exp", e}});
     };
 
@@ -936,9 +938,9 @@
         [&](const type::F32*) { return build_f32(); },  //
         [&](const type::F16*) { return build_f16(); },  //
         [&](const type::AbstractFloat*) {
-            auto* f = state.builder.create<sem::Vector>(el, n.Value());
-            auto* e = state.builder.create<sem::Vector>(state.builder.create<type::AbstractInt>(),
-                                                        n.Value());
+            auto* f = state.builder.create<type::Vector>(el, n.Value());
+            auto* e = state.builder.create<type::Vector>(state.builder.create<type::AbstractInt>(),
+                                                         n.Value());
             auto* abstract =
                 build_struct(state.builder, prefix + "_abstract", {{"fract", f}, {"exp", e}});
             abstract->SetConcreteTypes(utils::Vector{build_f32(), build_f16()});
diff --git a/src/tint/resolver/intrinsic_table_test.cc b/src/tint/resolver/intrinsic_table_test.cc
index 4d468fa..c24606e 100644
--- a/src/tint/resolver/intrinsic_table_test.cc
+++ b/src/tint/resolver/intrinsic_table_test.cc
@@ -74,7 +74,7 @@
 TEST_F(IntrinsicTableTest, MatchU32) {
     auto* f32 = create<type::F32>();
     auto* u32 = create<type::U32>();
-    auto* vec2_f32 = create<sem::Vector>(f32, 2u);
+    auto* vec2_f32 = create<type::Vector>(f32, 2u);
     auto result = table->Lookup(BuiltinType::kUnpack2X16Float, utils::Vector{u32},
                                 sem::EvaluationStage::kConstant, Source{});
     ASSERT_NE(result.sem, nullptr) << Diagnostics().str();
@@ -96,7 +96,7 @@
 TEST_F(IntrinsicTableTest, MatchI32) {
     auto* f32 = create<type::F32>();
     auto* i32 = create<type::I32>();
-    auto* vec4_f32 = create<sem::Vector>(f32, 4u);
+    auto* vec4_f32 = create<type::Vector>(f32, 4u);
     auto* tex = create<type::SampledTexture>(ast::TextureDimension::k1d, f32);
     auto result = table->Lookup(BuiltinType::kTextureLoad, utils::Vector{tex, i32, i32},
                                 sem::EvaluationStage::kConstant, Source{});
@@ -278,8 +278,8 @@
 
 TEST_F(IntrinsicTableTest, MatchSampler) {
     auto* f32 = create<type::F32>();
-    auto* vec2_f32 = create<sem::Vector>(f32, 2u);
-    auto* vec4_f32 = create<sem::Vector>(f32, 4u);
+    auto* vec2_f32 = create<type::Vector>(f32, 2u);
+    auto* vec4_f32 = create<type::Vector>(f32, 4u);
     auto* tex = create<type::SampledTexture>(ast::TextureDimension::k2d, f32);
     auto* sampler = create<type::Sampler>(ast::SamplerKind::kSampler);
     auto result = table->Lookup(BuiltinType::kTextureSample, utils::Vector{tex, sampler, vec2_f32},
@@ -299,7 +299,7 @@
 
 TEST_F(IntrinsicTableTest, MismatchSampler) {
     auto* f32 = create<type::F32>();
-    auto* vec2_f32 = create<sem::Vector>(f32, 2u);
+    auto* vec2_f32 = create<type::Vector>(f32, 2u);
     auto* tex = create<type::SampledTexture>(ast::TextureDimension::k2d, f32);
     auto result = table->Lookup(BuiltinType::kTextureSample, utils::Vector{tex, f32, vec2_f32},
                                 sem::EvaluationStage::kConstant, Source{});
@@ -310,8 +310,8 @@
 TEST_F(IntrinsicTableTest, MatchSampledTexture) {
     auto* i32 = create<type::I32>();
     auto* f32 = create<type::F32>();
-    auto* vec2_i32 = create<sem::Vector>(i32, 2u);
-    auto* vec4_f32 = create<sem::Vector>(f32, 4u);
+    auto* vec2_i32 = create<type::Vector>(i32, 2u);
+    auto* vec4_f32 = create<type::Vector>(f32, 4u);
     auto* tex = create<type::SampledTexture>(ast::TextureDimension::k2d, f32);
     auto result = table->Lookup(BuiltinType::kTextureLoad, utils::Vector{tex, vec2_i32, i32},
                                 sem::EvaluationStage::kConstant, Source{});
@@ -331,8 +331,8 @@
 TEST_F(IntrinsicTableTest, MatchMultisampledTexture) {
     auto* i32 = create<type::I32>();
     auto* f32 = create<type::F32>();
-    auto* vec2_i32 = create<sem::Vector>(i32, 2u);
-    auto* vec4_f32 = create<sem::Vector>(f32, 4u);
+    auto* vec2_i32 = create<type::Vector>(i32, 2u);
+    auto* vec4_f32 = create<type::Vector>(f32, 4u);
     auto* tex = create<type::MultisampledTexture>(ast::TextureDimension::k2d, f32);
     auto result = table->Lookup(BuiltinType::kTextureLoad, utils::Vector{tex, vec2_i32, i32},
                                 sem::EvaluationStage::kConstant, Source{});
@@ -352,7 +352,7 @@
 TEST_F(IntrinsicTableTest, MatchDepthTexture) {
     auto* f32 = create<type::F32>();
     auto* i32 = create<type::I32>();
-    auto* vec2_i32 = create<sem::Vector>(i32, 2u);
+    auto* vec2_i32 = create<type::Vector>(i32, 2u);
     auto* tex = create<type::DepthTexture>(ast::TextureDimension::k2d);
     auto result = table->Lookup(BuiltinType::kTextureLoad, utils::Vector{tex, vec2_i32, i32},
                                 sem::EvaluationStage::kConstant, Source{});
@@ -372,7 +372,7 @@
 TEST_F(IntrinsicTableTest, MatchDepthMultisampledTexture) {
     auto* f32 = create<type::F32>();
     auto* i32 = create<type::I32>();
-    auto* vec2_i32 = create<sem::Vector>(i32, 2u);
+    auto* vec2_i32 = create<type::Vector>(i32, 2u);
     auto* tex = create<type::DepthMultisampledTexture>(ast::TextureDimension::k2d);
     auto result = table->Lookup(BuiltinType::kTextureLoad, utils::Vector{tex, vec2_i32, i32},
                                 sem::EvaluationStage::kConstant, Source{});
@@ -392,8 +392,8 @@
 TEST_F(IntrinsicTableTest, MatchExternalTexture) {
     auto* f32 = create<type::F32>();
     auto* i32 = create<type::I32>();
-    auto* vec2_i32 = create<sem::Vector>(i32, 2u);
-    auto* vec4_f32 = create<sem::Vector>(f32, 4u);
+    auto* vec2_i32 = create<type::Vector>(i32, 2u);
+    auto* vec4_f32 = create<type::Vector>(f32, 4u);
     auto* tex = create<type::ExternalTexture>();
     auto result = table->Lookup(BuiltinType::kTextureLoad, utils::Vector{tex, vec2_i32},
                                 sem::EvaluationStage::kConstant, Source{});
@@ -411,8 +411,8 @@
 TEST_F(IntrinsicTableTest, MatchWOStorageTexture) {
     auto* f32 = create<type::F32>();
     auto* i32 = create<type::I32>();
-    auto* vec2_i32 = create<sem::Vector>(i32, 2u);
-    auto* vec4_f32 = create<sem::Vector>(f32, 4u);
+    auto* vec2_i32 = create<type::Vector>(i32, 2u);
+    auto* vec4_f32 = create<type::Vector>(f32, 4u);
     auto* subtype = type::StorageTexture::SubtypeFor(ast::TexelFormat::kR32Float, Types());
     auto* tex = create<type::StorageTexture>(
         ast::TextureDimension::k2d, ast::TexelFormat::kR32Float, ast::Access::kWrite, subtype);
@@ -435,7 +435,7 @@
 TEST_F(IntrinsicTableTest, MismatchTexture) {
     auto* f32 = create<type::F32>();
     auto* i32 = create<type::I32>();
-    auto* vec2_i32 = create<sem::Vector>(i32, 2u);
+    auto* vec2_i32 = create<type::Vector>(i32, 2u);
     auto result = table->Lookup(BuiltinType::kTextureLoad, utils::Vector{f32, vec2_i32},
                                 sem::EvaluationStage::kConstant, Source{});
     ASSERT_EQ(result.sem, nullptr);
@@ -482,7 +482,7 @@
 
 TEST_F(IntrinsicTableTest, MatchOpenSizeVector) {
     auto* f32 = create<type::F32>();
-    auto* vec2_f32 = create<sem::Vector>(f32, 2u);
+    auto* vec2_f32 = create<type::Vector>(f32, 2u);
     auto result = table->Lookup(BuiltinType::kClamp, utils::Vector{vec2_f32, vec2_f32, vec2_f32},
                                 sem::EvaluationStage::kConstant, Source{});
     ASSERT_NE(result.sem, nullptr) << Diagnostics().str();
@@ -498,7 +498,7 @@
 TEST_F(IntrinsicTableTest, MismatchOpenSizeVector) {
     auto* f32 = create<type::F32>();
     auto* u32 = create<type::U32>();
-    auto* vec2_f32 = create<sem::Vector>(f32, 2u);
+    auto* vec2_f32 = create<type::Vector>(f32, 2u);
     auto result = table->Lookup(BuiltinType::kClamp, utils::Vector{vec2_f32, u32, vec2_f32},
                                 sem::EvaluationStage::kConstant, Source{});
     ASSERT_EQ(result.sem, nullptr);
@@ -507,8 +507,8 @@
 
 TEST_F(IntrinsicTableTest, MatchOpenSizeMatrix) {
     auto* f32 = create<type::F32>();
-    auto* vec3_f32 = create<sem::Vector>(f32, 3u);
-    auto* mat3_f32 = create<sem::Matrix>(vec3_f32, 3u);
+    auto* vec3_f32 = create<type::Vector>(f32, 3u);
+    auto* mat3_f32 = create<type::Matrix>(vec3_f32, 3u);
     auto result = table->Lookup(BuiltinType::kDeterminant, utils::Vector{mat3_f32},
                                 sem::EvaluationStage::kConstant, Source{});
     ASSERT_NE(result.sem, nullptr) << Diagnostics().str();
@@ -521,8 +521,8 @@
 
 TEST_F(IntrinsicTableTest, MismatchOpenSizeMatrix) {
     auto* f32 = create<type::F32>();
-    auto* vec2_f32 = create<sem::Vector>(f32, 2u);
-    auto* mat3x2_f32 = create<sem::Matrix>(vec2_f32, 3u);
+    auto* vec2_f32 = create<type::Vector>(f32, 2u);
+    auto* mat3x2_f32 = create<type::Matrix>(vec2_f32, 3u);
     auto result = table->Lookup(BuiltinType::kDeterminant, utils::Vector{mat3x2_f32},
                                 sem::EvaluationStage::kConstant, Source{});
     ASSERT_EQ(result.sem, nullptr);
@@ -669,7 +669,7 @@
 
 TEST_F(IntrinsicTableTest, SameOverloadReturnsSameBuiltinPointer) {
     auto* f32 = create<type::F32>();
-    auto* vec2_f32 = create<sem::Vector>(create<type::F32>(), 2u);
+    auto* vec2_f32 = create<type::Vector>(create<type::F32>(), 2u);
     auto* bool_ = create<type::Bool>();
     auto a = table->Lookup(BuiltinType::kSelect, utils::Vector{f32, f32, bool_},
                            sem::EvaluationStage::kConstant, Source{});
@@ -692,7 +692,7 @@
 
 TEST_F(IntrinsicTableTest, MatchUnaryOp) {
     auto* i32 = create<type::I32>();
-    auto* vec3_i32 = create<sem::Vector>(i32, 3u);
+    auto* vec3_i32 = create<type::Vector>(i32, 3u);
     auto result = table->Lookup(ast::UnaryOp::kNegation, vec3_i32, sem::EvaluationStage::kConstant,
                                 Source{{12, 34}});
     EXPECT_EQ(result.result, vec3_i32);
@@ -731,7 +731,7 @@
 
 TEST_F(IntrinsicTableTest, MatchBinaryOp) {
     auto* i32 = create<type::I32>();
-    auto* vec3_i32 = create<sem::Vector>(i32, 3u);
+    auto* vec3_i32 = create<type::Vector>(i32, 3u);
     auto result = table->Lookup(ast::BinaryOp::kMultiply, i32, vec3_i32,
                                 sem::EvaluationStage::kConstant, Source{{12, 34}},
                                 /* is_compound */ false);
@@ -765,7 +765,7 @@
 
 TEST_F(IntrinsicTableTest, MatchCompoundOp) {
     auto* i32 = create<type::I32>();
-    auto* vec3_i32 = create<sem::Vector>(i32, 3u);
+    auto* vec3_i32 = create<type::Vector>(i32, 3u);
     auto result = table->Lookup(ast::BinaryOp::kMultiply, i32, vec3_i32,
                                 sem::EvaluationStage::kConstant, Source{{12, 34}},
                                 /* is_compound */ true);
@@ -799,7 +799,7 @@
 
 TEST_F(IntrinsicTableTest, MatchTypeInitializerImplicit) {
     auto* i32 = create<type::I32>();
-    auto* vec3_i32 = create<sem::Vector>(i32, 3u);
+    auto* vec3_i32 = create<type::Vector>(i32, 3u);
     auto result = table->Lookup(InitConvIntrinsic::kVec3, nullptr, utils::Vector{i32, i32, i32},
                                 sem::EvaluationStage::kConstant, Source{{12, 34}});
     ASSERT_NE(result.target, nullptr);
@@ -814,7 +814,7 @@
 
 TEST_F(IntrinsicTableTest, MatchTypeInitializerExplicit) {
     auto* i32 = create<type::I32>();
-    auto* vec3_i32 = create<sem::Vector>(i32, 3u);
+    auto* vec3_i32 = create<type::Vector>(i32, 3u);
     auto result = table->Lookup(InitConvIntrinsic::kVec3, i32, utils::Vector{i32, i32, i32},
                                 sem::EvaluationStage::kConstant, Source{{12, 34}});
     ASSERT_NE(result.target, nullptr);
@@ -881,7 +881,7 @@
 
 TEST_F(IntrinsicTableTest, MatchTypeInitializerImplicitVecFromVecAbstract) {
     auto* ai = create<type::AbstractInt>();
-    auto* vec3_ai = create<sem::Vector>(ai, 3u);
+    auto* vec3_ai = create<type::Vector>(ai, 3u);
     auto result = table->Lookup(InitConvIntrinsic::kVec3, nullptr, utils::Vector{vec3_ai},
                                 sem::EvaluationStage::kConstant, Source{{12, 34}});
     ASSERT_NE(result.target, nullptr);
@@ -894,9 +894,9 @@
 
 TEST_F(IntrinsicTableTest, MatchTypeInitializerImplicitMatFromVec) {
     auto* af = create<type::AbstractFloat>();
-    auto* vec2_ai = create<sem::Vector>(create<type::AbstractInt>(), 2u);
-    auto* vec2_af = create<sem::Vector>(af, 2u);
-    auto* mat2x2_af = create<sem::Matrix>(vec2_af, 2u);
+    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(InitConvIntrinsic::kMat2x2, nullptr, utils::Vector{vec2_ai, vec2_ai},
                       sem::EvaluationStage::kConstant, Source{{12, 34}});
@@ -911,7 +911,7 @@
 
 TEST_F(IntrinsicTableTest, MatchTypeInitializer_ConstantEval) {
     auto* ai = create<type::AbstractInt>();
-    auto* vec3_ai = create<sem::Vector>(ai, 3u);
+    auto* vec3_ai = create<type::Vector>(ai, 3u);
     auto result = table->Lookup(InitConvIntrinsic::kVec3, nullptr, utils::Vector{ai, ai, ai},
                                 sem::EvaluationStage::kConstant, Source{{12, 34}});
     ASSERT_NE(result.target, nullptr);
@@ -930,7 +930,7 @@
     auto result = table->Lookup(InitConvIntrinsic::kVec3, nullptr, utils::Vector{ai, ai, ai},
                                 sem::EvaluationStage::kRuntime, Source{{12, 34}});
     auto* i32 = create<type::I32>();
-    auto* vec3_i32 = create<sem::Vector>(i32, 3u);
+    auto* vec3_i32 = create<type::Vector>(i32, 3u);
     ASSERT_NE(result.target, nullptr);
     EXPECT_EQ(result.target->Stage(), sem::EvaluationStage::kConstant);
     EXPECT_EQ(result.target->ReturnType(), vec3_i32);
@@ -944,9 +944,9 @@
 
 TEST_F(IntrinsicTableTest, MatchTypeConversion) {
     auto* i32 = create<type::I32>();
-    auto* vec3_i32 = create<sem::Vector>(i32, 3u);
+    auto* vec3_i32 = create<type::Vector>(i32, 3u);
     auto* f32 = create<type::F32>();
-    auto* vec3_f32 = create<sem::Vector>(f32, 3u);
+    auto* vec3_f32 = create<type::Vector>(f32, 3u);
     auto result = table->Lookup(InitConvIntrinsic::kVec3, i32, utils::Vector{vec3_f32},
                                 sem::EvaluationStage::kConstant, Source{{12, 34}});
     ASSERT_NE(result.target, nullptr);
@@ -986,9 +986,9 @@
 TEST_F(IntrinsicTableTest, MatchTypeConversion_ConstantEval) {
     auto* ai = create<type::AbstractInt>();
     auto* af = create<type::AbstractFloat>();
-    auto* vec3_ai = create<sem::Vector>(ai, 3u);
+    auto* vec3_ai = create<type::Vector>(ai, 3u);
     auto* f32 = create<type::F32>();
-    auto* vec3_f32 = create<sem::Vector>(f32, 3u);
+    auto* vec3_f32 = create<type::Vector>(f32, 3u);
     auto result = table->Lookup(InitConvIntrinsic::kVec3, af, utils::Vector{vec3_ai},
                                 sem::EvaluationStage::kConstant, Source{{12, 34}});
     ASSERT_NE(result.target, nullptr);
@@ -1003,9 +1003,9 @@
 TEST_F(IntrinsicTableTest, MatchTypeConversion_RuntimeEval) {
     auto* ai = create<type::AbstractInt>();
     auto* af = create<type::AbstractFloat>();
-    auto* vec3_ai = create<sem::Vector>(ai, 3u);
-    auto* vec3_f32 = create<sem::Vector>(create<type::F32>(), 3u);
-    auto* vec3_i32 = create<sem::Vector>(create<type::I32>(), 3u);
+    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(InitConvIntrinsic::kVec3, af, utils::Vector{vec3_ai},
                                 sem::EvaluationStage::kRuntime, Source{{12, 34}});
     ASSERT_NE(result.target, nullptr);
diff --git a/src/tint/resolver/is_host_shareable_test.cc b/src/tint/resolver/is_host_shareable_test.cc
index e2fb104..f4efbe9 100644
--- a/src/tint/resolver/is_host_shareable_test.cc
+++ b/src/tint/resolver/is_host_shareable_test.cc
@@ -39,59 +39,59 @@
 }
 
 TEST_F(ResolverIsHostShareable, NumericVector) {
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Vector>(create<type::I32>(), 2u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Vector>(create<type::I32>(), 3u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Vector>(create<type::I32>(), 4u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Vector>(create<type::U32>(), 2u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Vector>(create<type::U32>(), 3u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Vector>(create<type::U32>(), 4u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Vector>(create<type::F32>(), 2u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Vector>(create<type::F32>(), 3u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Vector>(create<type::F32>(), 4u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Vector>(create<type::F16>(), 2u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Vector>(create<type::F16>(), 3u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Vector>(create<type::F16>(), 4u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Vector>(create<type::I32>(), 2u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Vector>(create<type::I32>(), 3u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Vector>(create<type::I32>(), 4u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Vector>(create<type::U32>(), 2u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Vector>(create<type::U32>(), 3u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Vector>(create<type::U32>(), 4u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Vector>(create<type::F32>(), 2u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Vector>(create<type::F32>(), 3u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Vector>(create<type::F32>(), 4u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Vector>(create<type::F16>(), 2u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Vector>(create<type::F16>(), 3u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Vector>(create<type::F16>(), 4u)));
 }
 
 TEST_F(ResolverIsHostShareable, BoolVector) {
-    EXPECT_FALSE(r()->IsHostShareable(create<sem::Vector>(create<type::Bool>(), 2u)));
-    EXPECT_FALSE(r()->IsHostShareable(create<sem::Vector>(create<type::Bool>(), 3u)));
-    EXPECT_FALSE(r()->IsHostShareable(create<sem::Vector>(create<type::Bool>(), 4u)));
-    EXPECT_FALSE(r()->IsHostShareable(create<sem::Vector>(create<type::Bool>(), 2u)));
-    EXPECT_FALSE(r()->IsHostShareable(create<sem::Vector>(create<type::Bool>(), 3u)));
-    EXPECT_FALSE(r()->IsHostShareable(create<sem::Vector>(create<type::Bool>(), 4u)));
-    EXPECT_FALSE(r()->IsHostShareable(create<sem::Vector>(create<type::Bool>(), 2u)));
-    EXPECT_FALSE(r()->IsHostShareable(create<sem::Vector>(create<type::Bool>(), 3u)));
-    EXPECT_FALSE(r()->IsHostShareable(create<sem::Vector>(create<type::Bool>(), 4u)));
+    EXPECT_FALSE(r()->IsHostShareable(create<type::Vector>(create<type::Bool>(), 2u)));
+    EXPECT_FALSE(r()->IsHostShareable(create<type::Vector>(create<type::Bool>(), 3u)));
+    EXPECT_FALSE(r()->IsHostShareable(create<type::Vector>(create<type::Bool>(), 4u)));
+    EXPECT_FALSE(r()->IsHostShareable(create<type::Vector>(create<type::Bool>(), 2u)));
+    EXPECT_FALSE(r()->IsHostShareable(create<type::Vector>(create<type::Bool>(), 3u)));
+    EXPECT_FALSE(r()->IsHostShareable(create<type::Vector>(create<type::Bool>(), 4u)));
+    EXPECT_FALSE(r()->IsHostShareable(create<type::Vector>(create<type::Bool>(), 2u)));
+    EXPECT_FALSE(r()->IsHostShareable(create<type::Vector>(create<type::Bool>(), 3u)));
+    EXPECT_FALSE(r()->IsHostShareable(create<type::Vector>(create<type::Bool>(), 4u)));
 }
 
 TEST_F(ResolverIsHostShareable, Matrix) {
-    auto* vec2_f32 = create<sem::Vector>(create<type::F32>(), 2u);
-    auto* vec3_f32 = create<sem::Vector>(create<type::F32>(), 3u);
-    auto* vec4_f32 = create<sem::Vector>(create<type::F32>(), 4u);
-    auto* vec2_f16 = create<sem::Vector>(create<type::F16>(), 2u);
-    auto* vec3_f16 = create<sem::Vector>(create<type::F16>(), 3u);
-    auto* vec4_f16 = create<sem::Vector>(create<type::F16>(), 4u);
+    auto* vec2_f32 = create<type::Vector>(create<type::F32>(), 2u);
+    auto* vec3_f32 = create<type::Vector>(create<type::F32>(), 3u);
+    auto* vec4_f32 = create<type::Vector>(create<type::F32>(), 4u);
+    auto* vec2_f16 = create<type::Vector>(create<type::F16>(), 2u);
+    auto* vec3_f16 = create<type::Vector>(create<type::F16>(), 3u);
+    auto* vec4_f16 = create<type::Vector>(create<type::F16>(), 4u);
 
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec2_f32, 2u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec2_f32, 3u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec2_f32, 4u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec3_f32, 2u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec3_f32, 3u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec3_f32, 4u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec4_f32, 2u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec4_f32, 3u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec4_f32, 4u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec2_f32, 2u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec2_f32, 3u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec2_f32, 4u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec3_f32, 2u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec3_f32, 3u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec3_f32, 4u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec4_f32, 2u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec4_f32, 3u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec4_f32, 4u)));
 
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec2_f16, 2u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec2_f16, 3u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec2_f16, 4u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec3_f16, 2u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec3_f16, 3u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec3_f16, 4u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec4_f16, 2u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec4_f16, 3u)));
-    EXPECT_TRUE(r()->IsHostShareable(create<sem::Matrix>(vec4_f16, 4u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec2_f16, 2u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec2_f16, 3u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec2_f16, 4u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec3_f16, 2u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec3_f16, 3u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec3_f16, 4u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec4_f16, 2u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec4_f16, 3u)));
+    EXPECT_TRUE(r()->IsHostShareable(create<type::Matrix>(vec4_f16, 4u)));
 }
 
 TEST_F(ResolverIsHostShareable, Pointer) {
diff --git a/src/tint/resolver/is_storeable_test.cc b/src/tint/resolver/is_storeable_test.cc
index 73368b4..793b8b1 100644
--- a/src/tint/resolver/is_storeable_test.cc
+++ b/src/tint/resolver/is_storeable_test.cc
@@ -36,45 +36,45 @@
 }
 
 TEST_F(ResolverIsStorableTest, Vector) {
-    EXPECT_TRUE(r()->IsStorable(create<sem::Vector>(create<type::I32>(), 2u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Vector>(create<type::I32>(), 3u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Vector>(create<type::I32>(), 4u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Vector>(create<type::U32>(), 2u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Vector>(create<type::U32>(), 3u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Vector>(create<type::U32>(), 4u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Vector>(create<type::F32>(), 2u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Vector>(create<type::F32>(), 3u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Vector>(create<type::F32>(), 4u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Vector>(create<type::F16>(), 2u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Vector>(create<type::F16>(), 3u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Vector>(create<type::F16>(), 4u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Vector>(create<type::I32>(), 2u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Vector>(create<type::I32>(), 3u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Vector>(create<type::I32>(), 4u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Vector>(create<type::U32>(), 2u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Vector>(create<type::U32>(), 3u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Vector>(create<type::U32>(), 4u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Vector>(create<type::F32>(), 2u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Vector>(create<type::F32>(), 3u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Vector>(create<type::F32>(), 4u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Vector>(create<type::F16>(), 2u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Vector>(create<type::F16>(), 3u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Vector>(create<type::F16>(), 4u)));
 }
 
 TEST_F(ResolverIsStorableTest, Matrix) {
-    auto* vec2_f32 = create<sem::Vector>(create<type::F32>(), 2u);
-    auto* vec3_f32 = create<sem::Vector>(create<type::F32>(), 3u);
-    auto* vec4_f32 = create<sem::Vector>(create<type::F32>(), 4u);
-    auto* vec2_f16 = create<sem::Vector>(create<type::F16>(), 2u);
-    auto* vec3_f16 = create<sem::Vector>(create<type::F16>(), 3u);
-    auto* vec4_f16 = create<sem::Vector>(create<type::F16>(), 4u);
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec2_f32, 2u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec2_f32, 3u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec2_f32, 4u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec3_f32, 2u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec3_f32, 3u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec3_f32, 4u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec4_f32, 2u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec4_f32, 3u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec4_f32, 4u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec2_f16, 2u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec2_f16, 3u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec2_f16, 4u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec3_f16, 2u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec3_f16, 3u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec3_f16, 4u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec4_f16, 2u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec4_f16, 3u)));
-    EXPECT_TRUE(r()->IsStorable(create<sem::Matrix>(vec4_f16, 4u)));
+    auto* vec2_f32 = create<type::Vector>(create<type::F32>(), 2u);
+    auto* vec3_f32 = create<type::Vector>(create<type::F32>(), 3u);
+    auto* vec4_f32 = create<type::Vector>(create<type::F32>(), 4u);
+    auto* vec2_f16 = create<type::Vector>(create<type::F16>(), 2u);
+    auto* vec3_f16 = create<type::Vector>(create<type::F16>(), 3u);
+    auto* vec4_f16 = create<type::Vector>(create<type::F16>(), 4u);
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec2_f32, 2u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec2_f32, 3u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec2_f32, 4u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec3_f32, 2u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec3_f32, 3u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec3_f32, 4u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec4_f32, 2u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec4_f32, 3u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec4_f32, 4u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec2_f16, 2u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec2_f16, 3u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec2_f16, 4u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec3_f16, 2u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec3_f16, 3u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec3_f16, 4u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec4_f16, 2u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec4_f16, 3u)));
+    EXPECT_TRUE(r()->IsStorable(create<type::Matrix>(vec4_f16, 4u)));
 }
 
 TEST_F(ResolverIsStorableTest, Pointer) {
diff --git a/src/tint/resolver/materialize_test.cc b/src/tint/resolver/materialize_test.cc
index 4451f9d..8c63c1f 100644
--- a/src/tint/resolver/materialize_test.cc
+++ b/src/tint/resolver/materialize_test.cc
@@ -96,7 +96,7 @@
 
         tint::Switch(
             expected_sem_ty,  //
-            [&](const sem::Vector* v) {
+            [&](const type::Vector* v) {
                 for (uint32_t i = 0; i < v->Width(); i++) {
                     auto* el = value->Index(i);
                     ASSERT_NE(el, nullptr);
@@ -104,7 +104,7 @@
                     EXPECT_EQ(std::get<T>(el->Value()), expected_value);
                 }
             },
-            [&](const sem::Matrix* m) {
+            [&](const type::Matrix* m) {
                 for (uint32_t c = 0; c < m->columns(); c++) {
                     auto* column = value->Index(c);
                     ASSERT_NE(column, nullptr);
@@ -1270,13 +1270,13 @@
     auto* materialize = sem->As<sem::Materialize>();
     ASSERT_TRUE(materialize->Type()->Is<sem::Struct>());
     auto* concrete_str = materialize->Type()->As<sem::Struct>();
-    ASSERT_TRUE(concrete_str->Members()[0]->Type()->Is<sem::Vector>());
-    ASSERT_TRUE(concrete_str->Members()[0]->Type()->As<sem::Vector>()->type()->Is<type::F32>());
+    ASSERT_TRUE(concrete_str->Members()[0]->Type()->Is<type::Vector>());
+    ASSERT_TRUE(concrete_str->Members()[0]->Type()->As<type::Vector>()->type()->Is<type::F32>());
     ASSERT_TRUE(materialize->Expr()->Type()->Is<sem::Struct>());
     auto* abstract_str = materialize->Expr()->Type()->As<sem::Struct>();
-    ASSERT_TRUE(abstract_str->Members()[0]->Type()->Is<sem::Vector>());
+    ASSERT_TRUE(abstract_str->Members()[0]->Type()->Is<type::Vector>());
     ASSERT_TRUE(
-        abstract_str->Members()[0]->Type()->As<sem::Vector>()->type()->Is<type::AbstractFloat>());
+        abstract_str->Members()[0]->Type()->As<type::Vector>()->type()->Is<type::AbstractFloat>());
 }
 
 TEST_F(MaterializeAbstractStructure, Modf_Scalar_ExplicitType) {
@@ -1311,13 +1311,13 @@
     auto* materialize = sem->As<sem::Materialize>();
     ASSERT_TRUE(materialize->Type()->Is<sem::Struct>());
     auto* concrete_str = materialize->Type()->As<sem::Struct>();
-    ASSERT_TRUE(concrete_str->Members()[0]->Type()->Is<sem::Vector>());
-    ASSERT_TRUE(concrete_str->Members()[0]->Type()->As<sem::Vector>()->type()->Is<type::F16>());
+    ASSERT_TRUE(concrete_str->Members()[0]->Type()->Is<type::Vector>());
+    ASSERT_TRUE(concrete_str->Members()[0]->Type()->As<type::Vector>()->type()->Is<type::F16>());
     ASSERT_TRUE(materialize->Expr()->Type()->Is<sem::Struct>());
     auto* abstract_str = materialize->Expr()->Type()->As<sem::Struct>();
-    ASSERT_TRUE(abstract_str->Members()[0]->Type()->Is<sem::Vector>());
+    ASSERT_TRUE(abstract_str->Members()[0]->Type()->Is<type::Vector>());
     ASSERT_TRUE(
-        abstract_str->Members()[0]->Type()->As<sem::Vector>()->type()->Is<type::AbstractFloat>());
+        abstract_str->Members()[0]->Type()->As<type::Vector>()->type()->Is<type::AbstractFloat>());
 }
 
 TEST_F(MaterializeAbstractStructure, Frexp_Scalar_DefaultType) {
@@ -1348,17 +1348,17 @@
     auto* materialize = sem->As<sem::Materialize>();
     ASSERT_TRUE(materialize->Type()->Is<sem::Struct>());
     auto* concrete_str = materialize->Type()->As<sem::Struct>();
-    ASSERT_TRUE(concrete_str->Members()[0]->Type()->Is<sem::Vector>());
-    ASSERT_TRUE(concrete_str->Members()[1]->Type()->Is<sem::Vector>());
-    ASSERT_TRUE(concrete_str->Members()[0]->Type()->As<sem::Vector>()->type()->Is<type::F32>());
-    ASSERT_TRUE(concrete_str->Members()[1]->Type()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(concrete_str->Members()[0]->Type()->Is<type::Vector>());
+    ASSERT_TRUE(concrete_str->Members()[1]->Type()->Is<type::Vector>());
+    ASSERT_TRUE(concrete_str->Members()[0]->Type()->As<type::Vector>()->type()->Is<type::F32>());
+    ASSERT_TRUE(concrete_str->Members()[1]->Type()->As<type::Vector>()->type()->Is<type::I32>());
     ASSERT_TRUE(materialize->Expr()->Type()->Is<sem::Struct>());
     auto* abstract_str = materialize->Expr()->Type()->As<sem::Struct>();
-    ASSERT_TRUE(abstract_str->Members()[0]->Type()->Is<sem::Vector>());
+    ASSERT_TRUE(abstract_str->Members()[0]->Type()->Is<type::Vector>());
     ASSERT_TRUE(
-        abstract_str->Members()[0]->Type()->As<sem::Vector>()->type()->Is<type::AbstractFloat>());
+        abstract_str->Members()[0]->Type()->As<type::Vector>()->type()->Is<type::AbstractFloat>());
     ASSERT_TRUE(
-        abstract_str->Members()[1]->Type()->As<sem::Vector>()->type()->Is<type::AbstractInt>());
+        abstract_str->Members()[1]->Type()->As<type::Vector>()->type()->Is<type::AbstractInt>());
 }
 
 TEST_F(MaterializeAbstractStructure, Frexp_Scalar_ExplicitType) {
@@ -1395,17 +1395,17 @@
     auto* materialize = sem->As<sem::Materialize>();
     ASSERT_TRUE(materialize->Type()->Is<sem::Struct>());
     auto* concrete_str = materialize->Type()->As<sem::Struct>();
-    ASSERT_TRUE(concrete_str->Members()[0]->Type()->Is<sem::Vector>());
-    ASSERT_TRUE(concrete_str->Members()[1]->Type()->Is<sem::Vector>());
-    ASSERT_TRUE(concrete_str->Members()[0]->Type()->As<sem::Vector>()->type()->Is<type::F16>());
-    ASSERT_TRUE(concrete_str->Members()[1]->Type()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(concrete_str->Members()[0]->Type()->Is<type::Vector>());
+    ASSERT_TRUE(concrete_str->Members()[1]->Type()->Is<type::Vector>());
+    ASSERT_TRUE(concrete_str->Members()[0]->Type()->As<type::Vector>()->type()->Is<type::F16>());
+    ASSERT_TRUE(concrete_str->Members()[1]->Type()->As<type::Vector>()->type()->Is<type::I32>());
     ASSERT_TRUE(materialize->Expr()->Type()->Is<sem::Struct>());
     auto* abstract_str = materialize->Expr()->Type()->As<sem::Struct>();
-    ASSERT_TRUE(abstract_str->Members()[0]->Type()->Is<sem::Vector>());
+    ASSERT_TRUE(abstract_str->Members()[0]->Type()->Is<type::Vector>());
     ASSERT_TRUE(
-        abstract_str->Members()[0]->Type()->As<sem::Vector>()->type()->Is<type::AbstractFloat>());
+        abstract_str->Members()[0]->Type()->As<type::Vector>()->type()->Is<type::AbstractFloat>());
     ASSERT_TRUE(
-        abstract_str->Members()[1]->Type()->As<sem::Vector>()->type()->Is<type::AbstractInt>());
+        abstract_str->Members()[1]->Type()->As<type::Vector>()->type()->Is<type::AbstractInt>());
 }
 
 }  // namespace materialize_abstract_structure
diff --git a/src/tint/resolver/resolver.cc b/src/tint/resolver/resolver.cc
index df7131c..826d6ce 100644
--- a/src/tint/resolver/resolver.cc
+++ b/src/tint/resolver/resolver.cc
@@ -216,13 +216,13 @@
             return builder_->create<type::F16>();
         },
         [&](const ast::F32*) { return builder_->create<type::F32>(); },
-        [&](const ast::Vector* t) -> sem::Vector* {
+        [&](const ast::Vector* t) -> type::Vector* {
             if (!t->type) {
                 AddError("missing vector element type", t->source.End());
                 return nullptr;
             }
             if (auto* el = Type(t->type)) {
-                if (auto* vector = builder_->create<sem::Vector>(el, t->width)) {
+                if (auto* vector = builder_->create<type::Vector>(el, t->width)) {
                     if (validator_.Vector(vector, t->source)) {
                         return vector;
                     }
@@ -230,14 +230,14 @@
             }
             return nullptr;
         },
-        [&](const ast::Matrix* t) -> sem::Matrix* {
+        [&](const ast::Matrix* t) -> type::Matrix* {
             if (!t->type) {
                 AddError("missing matrix element type", t->source.End());
                 return nullptr;
             }
             if (auto* el = Type(t->type)) {
-                if (auto* column_type = builder_->create<sem::Vector>(el, t->rows)) {
-                    if (auto* matrix = builder_->create<sem::Matrix>(column_type, t->columns)) {
+                if (auto* column_type = builder_->create<type::Vector>(el, t->rows)) {
+                    if (auto* matrix = builder_->create<type::Matrix>(column_type, t->columns)) {
                         if (validator_.Matrix(matrix, t->source)) {
                             return matrix;
                         }
@@ -1718,17 +1718,17 @@
                                          const Source& source) {
     auto i32 = [&] { return builder_->create<type::I32>(); };
     auto f32 = [&] { return builder_->create<type::F32>(); };
-    auto i32v = [&](uint32_t width) { return builder_->create<sem::Vector>(i32(), width); };
-    auto f32v = [&](uint32_t width) { return builder_->create<sem::Vector>(f32(), width); };
+    auto i32v = [&](uint32_t width) { return builder_->create<type::Vector>(i32(), width); };
+    auto f32v = [&](uint32_t width) { return builder_->create<type::Vector>(f32(), width); };
     auto f32m = [&](uint32_t columns, uint32_t rows) {
-        return builder_->create<sem::Matrix>(f32v(rows), columns);
+        return builder_->create<type::Matrix>(f32v(rows), columns);
     };
 
     return Switch(
         ty,  //
         [&](const type::AbstractInt*) { return target_ty ? target_ty : i32(); },
         [&](const type::AbstractFloat*) { return target_ty ? target_ty : f32(); },
-        [&](const sem::Vector* v) {
+        [&](const type::Vector* v) {
             return Switch(
                 v->type(),  //
                 [&](const type::AbstractInt*) { return target_ty ? target_ty : i32v(v->Width()); },
@@ -1736,7 +1736,7 @@
                     return target_ty ? target_ty : f32v(v->Width());
                 });
         },
-        [&](const sem::Matrix* m) {
+        [&](const type::Matrix* m) {
             return Switch(m->type(),  //
                           [&](const type::AbstractFloat*) {
                               return target_ty ? target_ty : f32m(m->columns(), m->rows());
@@ -1870,9 +1870,9 @@
     auto* ty = Switch(
         obj_ty,  //
         [&](const sem::Array* arr) { return arr->ElemType(); },
-        [&](const sem::Vector* vec) { return vec->type(); },
-        [&](const sem::Matrix* mat) {
-            return builder_->create<sem::Vector>(mat->type(), mat->rows());
+        [&](const type::Vector* vec) { return vec->type(); },
+        [&](const type::Matrix* mat) {
+            return builder_->create<type::Vector>(mat->type(), mat->rows());
         },
         [&](Default) {
             AddError("cannot index type '" + sem_.TypeNameOf(obj_ty) + "'", expr->source);
@@ -2034,10 +2034,10 @@
     auto ty_init_or_conv = [&](const type::Type* ty) {
         return Switch(
             ty,  //
-            [&](const sem::Vector* v) {
+            [&](const type::Vector* v) {
                 return ct_init_or_conv(VectorInitConvIntrinsic(v->Width()), v->type());
             },
-            [&](const sem::Matrix* m) {
+            [&](const type::Matrix* m) {
                 return ct_init_or_conv(MatrixInitConvIntrinsic(m->columns(), m->rows()), m->type());
             },
             [&](const type::I32*) { return ct_init_or_conv(InitConvIntrinsic::kI32, nullptr); },
@@ -2351,29 +2351,29 @@
     auto& b = *builder_;
     switch (type::ParseShortName(name)) {
         case type::ShortName::kVec2F:
-            return b.create<sem::Vector>(b.create<type::F32>(), 2u);
+            return b.create<type::Vector>(b.create<type::F32>(), 2u);
         case type::ShortName::kVec3F:
-            return b.create<sem::Vector>(b.create<type::F32>(), 3u);
+            return b.create<type::Vector>(b.create<type::F32>(), 3u);
         case type::ShortName::kVec4F:
-            return b.create<sem::Vector>(b.create<type::F32>(), 4u);
+            return b.create<type::Vector>(b.create<type::F32>(), 4u);
         case type::ShortName::kVec2H:
-            return b.create<sem::Vector>(b.create<type::F16>(), 2u);
+            return b.create<type::Vector>(b.create<type::F16>(), 2u);
         case type::ShortName::kVec3H:
-            return b.create<sem::Vector>(b.create<type::F16>(), 3u);
+            return b.create<type::Vector>(b.create<type::F16>(), 3u);
         case type::ShortName::kVec4H:
-            return b.create<sem::Vector>(b.create<type::F16>(), 4u);
+            return b.create<type::Vector>(b.create<type::F16>(), 4u);
         case type::ShortName::kVec2I:
-            return b.create<sem::Vector>(b.create<type::I32>(), 2u);
+            return b.create<type::Vector>(b.create<type::I32>(), 2u);
         case type::ShortName::kVec3I:
-            return b.create<sem::Vector>(b.create<type::I32>(), 3u);
+            return b.create<type::Vector>(b.create<type::I32>(), 3u);
         case type::ShortName::kVec4I:
-            return b.create<sem::Vector>(b.create<type::I32>(), 4u);
+            return b.create<type::Vector>(b.create<type::I32>(), 4u);
         case type::ShortName::kVec2U:
-            return b.create<sem::Vector>(b.create<type::U32>(), 2u);
+            return b.create<type::Vector>(b.create<type::U32>(), 2u);
         case type::ShortName::kVec3U:
-            return b.create<sem::Vector>(b.create<type::U32>(), 3u);
+            return b.create<type::Vector>(b.create<type::U32>(), 3u);
         case type::ShortName::kVec4U:
-            return b.create<sem::Vector>(b.create<type::U32>(), 4u);
+            return b.create<type::Vector>(b.create<type::U32>(), 4u);
         case type::ShortName::kUndefined:
             break;
     }
@@ -2677,7 +2677,7 @@
                                                              has_side_effects, root_ident);
         },
 
-        [&](const sem::Vector* vec) -> sem::Expression* {
+        [&](const type::Vector* vec) -> sem::Expression* {
             Mark(expr->member);
             std::string s = builder_->Symbols().NameFor(expr->member->symbol);
             auto size = s.size();
@@ -2739,7 +2739,7 @@
             } else {
                 // The vector will have a number of components equal to the length of
                 // the swizzle.
-                ty = builder_->create<sem::Vector>(vec->type(), static_cast<uint32_t>(size));
+                ty = builder_->create<type::Vector>(vec->type(), static_cast<uint32_t>(size));
             }
             auto val = const_eval_.Swizzle(ty, object, swizzle);
             if (!val) {
@@ -2837,8 +2837,8 @@
 
                 auto* array = unary->expr->As<ast::IndexAccessorExpression>();
                 auto* member = unary->expr->As<ast::MemberAccessorExpression>();
-                if ((array && sem_.TypeOf(array->object)->UnwrapRef()->Is<sem::Vector>()) ||
-                    (member && sem_.TypeOf(member->structure)->UnwrapRef()->Is<sem::Vector>())) {
+                if ((array && sem_.TypeOf(array->object)->UnwrapRef()->Is<type::Vector>()) ||
+                    (member && sem_.TypeOf(member->structure)->UnwrapRef()->Is<type::Vector>())) {
                     AddError("cannot take the address of a vector component", unary->expr->source);
                     return nullptr;
                 }
diff --git a/src/tint/resolver/resolver_test.cc b/src/tint/resolver/resolver_test.cc
index b64290a..bb67764 100644
--- a/src/tint/resolver/resolver_test.cc
+++ b/src/tint/resolver/resolver_test.cc
@@ -669,9 +669,9 @@
     EXPECT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 2u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 2u);
 }
 
 TEST_F(ResolverTest, Expr_Initializer_Type_Vec3) {
@@ -681,9 +681,9 @@
     EXPECT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 3u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 3u);
 }
 
 TEST_F(ResolverTest, Expr_Initializer_Type_Vec4) {
@@ -693,9 +693,9 @@
     EXPECT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 4u);
 }
 
 TEST_F(ResolverTest, Expr_Identifier_GlobalVariable) {
@@ -1294,9 +1294,9 @@
     EXPECT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(mem), nullptr);
-    ASSERT_TRUE(TypeOf(mem)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(mem)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(mem)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(mem)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(mem)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(mem)->As<type::Vector>()->Width(), 4u);
     auto* sma = Sem().Get(mem)->As<sem::Swizzle>();
     ASSERT_NE(sma, nullptr);
     EXPECT_EQ(sma->Object()->Declaration(), mem->structure);
@@ -1349,9 +1349,9 @@
     EXPECT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(mem), nullptr);
-    ASSERT_TRUE(TypeOf(mem)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(mem)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(mem)->As<sem::Vector>()->Width(), 2u);
+    ASSERT_TRUE(TypeOf(mem)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(mem)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(mem)->As<type::Vector>()->Width(), 2u);
     ASSERT_TRUE(Sem().Get(mem)->Is<sem::Swizzle>());
 }
 
@@ -1773,12 +1773,12 @@
     if (vec_by_mat) {
         lhs_type = ty.vec<f32>(vec_size);
         rhs_type = ty.mat<f32>(mat_cols, mat_rows);
-        result_type = create<sem::Vector>(create<type::F32>(), mat_cols);
+        result_type = create<type::Vector>(create<type::F32>(), mat_cols);
         is_valid_expr = vec_size == mat_rows;
     } else {
         lhs_type = ty.mat<f32>(mat_cols, mat_rows);
         rhs_type = ty.vec<f32>(vec_size);
-        result_type = create<sem::Vector>(create<type::F32>(), mat_rows);
+        result_type = create<type::Vector>(create<type::F32>(), mat_rows);
         is_valid_expr = vec_size == mat_cols;
     }
 
@@ -1816,8 +1816,8 @@
     auto* rhs_type = ty.mat<f32>(rhs_mat_cols, rhs_mat_rows);
 
     auto* f32 = create<type::F32>();
-    auto* col = create<sem::Vector>(f32, lhs_mat_rows);
-    auto* result_type = create<sem::Matrix>(col, rhs_mat_cols);
+    auto* col = create<type::Vector>(f32, lhs_mat_rows);
+    auto* result_type = create<type::Matrix>(col, rhs_mat_cols);
 
     GlobalVar("lhs", lhs_type, ast::AddressSpace::kPrivate);
     GlobalVar("rhs", rhs_type, ast::AddressSpace::kPrivate);
@@ -1860,15 +1860,15 @@
     EXPECT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(der), nullptr);
-    ASSERT_TRUE(TypeOf(der)->Is<sem::Vector>());
+    ASSERT_TRUE(TypeOf(der)->Is<type::Vector>());
     if (op == ast::UnaryOp::kNot) {
-        EXPECT_TRUE(TypeOf(der)->As<sem::Vector>()->type()->Is<type::Bool>());
+        EXPECT_TRUE(TypeOf(der)->As<type::Vector>()->type()->Is<type::Bool>());
     } else if (op == ast::UnaryOp::kNegation || op == ast::UnaryOp::kComplement) {
-        EXPECT_TRUE(TypeOf(der)->As<sem::Vector>()->type()->Is<type::I32>());
+        EXPECT_TRUE(TypeOf(der)->As<type::Vector>()->type()->Is<type::I32>());
     } else {
-        EXPECT_TRUE(TypeOf(der)->As<sem::Vector>()->type()->Is<type::F32>());
+        EXPECT_TRUE(TypeOf(der)->As<type::Vector>()->type()->Is<type::F32>());
     }
-    EXPECT_EQ(TypeOf(der)->As<sem::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(der)->As<type::Vector>()->Width(), 4u);
 }
 INSTANTIATE_TEST_SUITE_P(ResolverTest,
                          UnaryOpExpressionTest,
diff --git a/src/tint/resolver/resolver_test_helper.h b/src/tint/resolver/resolver_test_helper.h
index 83e1a5b..8829a53 100644
--- a/src/tint/resolver/resolver_test_helper.h
+++ b/src/tint/resolver/resolver_test_helper.h
@@ -452,7 +452,7 @@
     /// @param b the ProgramBuilder
     /// @return the semantic vector type
     static inline const type::Type* Sem(ProgramBuilder& b) {
-        return b.create<sem::Vector>(DataType<T>::Sem(b), N);
+        return b.create<type::Vector>(DataType<T>::Sem(b), N);
     }
     /// @param b the ProgramBuilder
     /// @param args args of size 1 or N with values of type T to initialize with
@@ -500,8 +500,8 @@
     /// @param b the ProgramBuilder
     /// @return the semantic matrix type
     static inline const type::Type* Sem(ProgramBuilder& b) {
-        auto* column_type = b.create<sem::Vector>(DataType<T>::Sem(b), M);
-        return b.create<sem::Matrix>(column_type, N);
+        auto* column_type = b.create<type::Vector>(DataType<T>::Sem(b), M);
+        return b.create<type::Matrix>(column_type, N);
     }
     /// @param b the ProgramBuilder
     /// @param args args of size 1 or N*M with values of type T to initialize with
diff --git a/src/tint/resolver/type_initializer_validation_test.cc b/src/tint/resolver/type_initializer_validation_test.cc
index 053fba1..f38823d 100644
--- a/src/tint/resolver/type_initializer_validation_test.cc
+++ b/src/tint/resolver/type_initializer_validation_test.cc
@@ -631,10 +631,10 @@
     ASSERT_NE(ctor, nullptr);
     EXPECT_EQ(call->Type(), ctor->ReturnType());
     ASSERT_EQ(ctor->Parameters().Length(), 2u);
-    ASSERT_TRUE(ctor->Parameters()[0]->Type()->Is<sem::Vector>());
-    EXPECT_TRUE(ctor->Parameters()[0]->Type()->As<sem::Vector>()->type()->Is<type::I32>());
-    ASSERT_TRUE(ctor->Parameters()[1]->Type()->Is<sem::Vector>());
-    EXPECT_TRUE(ctor->Parameters()[1]->Type()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(ctor->Parameters()[0]->Type()->Is<type::Vector>());
+    EXPECT_TRUE(ctor->Parameters()[0]->Type()->As<type::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(ctor->Parameters()[1]->Type()->Is<type::Vector>());
+    EXPECT_TRUE(ctor->Parameters()[1]->Type()->As<type::Vector>()->type()->Is<type::I32>());
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, InferredArrayU32_VecAI_VecF32) {
@@ -653,10 +653,10 @@
     ASSERT_NE(ctor, nullptr);
     EXPECT_EQ(call->Type(), ctor->ReturnType());
     ASSERT_EQ(ctor->Parameters().Length(), 2u);
-    ASSERT_TRUE(ctor->Parameters()[0]->Type()->Is<sem::Vector>());
-    EXPECT_TRUE(ctor->Parameters()[0]->Type()->As<sem::Vector>()->type()->Is<type::F32>());
-    ASSERT_TRUE(ctor->Parameters()[1]->Type()->Is<sem::Vector>());
-    EXPECT_TRUE(ctor->Parameters()[1]->Type()->As<sem::Vector>()->type()->Is<type::F32>());
+    ASSERT_TRUE(ctor->Parameters()[0]->Type()->Is<type::Vector>());
+    EXPECT_TRUE(ctor->Parameters()[0]->Type()->As<type::Vector>()->type()->Is<type::F32>());
+    ASSERT_TRUE(ctor->Parameters()[1]->Type()->Is<type::Vector>());
+    EXPECT_TRUE(ctor->Parameters()[1]->Type()->As<type::Vector>()->type()->Is<type::F32>());
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, ArrayArgumentTypeMismatch_U32F32) {
@@ -1141,9 +1141,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 2u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 2u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1160,9 +1160,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 2u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 2u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1183,9 +1183,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F16>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 2u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F16>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 2u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1204,9 +1204,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::U32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 2u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::U32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 2u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1225,9 +1225,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::I32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 2u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::I32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 2u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1246,9 +1246,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::Bool>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 2u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::Bool>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 2u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1267,9 +1267,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 2u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 2u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1277,7 +1277,7 @@
     ASSERT_NE(ctor, nullptr);
     EXPECT_EQ(call->Type(), ctor->ReturnType());
     ASSERT_EQ(ctor->Parameters().Length(), 1u);
-    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<sem::Vector>());
+    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<type::Vector>());
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec2_Success_Vec2TypeConversion) {
@@ -1287,9 +1287,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 2u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 2u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1297,7 +1297,7 @@
     ASSERT_NE(ctor, nullptr);
     EXPECT_EQ(call->Type(), ctor->ReturnType());
     ASSERT_EQ(ctor->Parameters().Length(), 1u);
-    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<sem::Vector>());
+    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<type::Vector>());
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec3F32_Error_ScalarArgumentTypeMismatch) {
@@ -1416,9 +1416,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 3u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 3u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1435,9 +1435,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 3u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 3u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1459,9 +1459,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F16>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 3u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F16>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 3u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1481,9 +1481,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::U32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 3u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::U32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 3u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1503,9 +1503,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::I32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 3u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::I32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 3u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1525,9 +1525,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::Bool>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 3u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::Bool>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 3u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1547,9 +1547,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 3u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 3u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1557,7 +1557,7 @@
     ASSERT_NE(ctor, nullptr);
     EXPECT_EQ(call->Type(), ctor->ReturnType());
     ASSERT_EQ(ctor->Parameters().Length(), 2u);
-    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<sem::Vector>());
+    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<type::Vector>());
     EXPECT_TRUE(ctor->Parameters()[1]->Type()->Is<type::F32>());
 }
 
@@ -1568,9 +1568,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 3u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 3u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1579,7 +1579,7 @@
     EXPECT_EQ(call->Type(), ctor->ReturnType());
     ASSERT_EQ(ctor->Parameters().Length(), 2u);
     EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<type::F32>());
-    EXPECT_TRUE(ctor->Parameters()[1]->Type()->Is<sem::Vector>());
+    EXPECT_TRUE(ctor->Parameters()[1]->Type()->Is<type::Vector>());
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec3_Success_Identity) {
@@ -1589,9 +1589,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 3u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 3u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1599,7 +1599,7 @@
     ASSERT_NE(ctor, nullptr);
     EXPECT_EQ(call->Type(), ctor->ReturnType());
     ASSERT_EQ(ctor->Parameters().Length(), 1u);
-    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<sem::Vector>());
+    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<type::Vector>());
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec3_Success_Vec3TypeConversion) {
@@ -1609,9 +1609,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 3u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 3u);
 
     auto* call = Sem().Get<sem::Call>(tc);
     ASSERT_NE(call, nullptr);
@@ -1619,7 +1619,7 @@
     ASSERT_NE(ctor, nullptr);
     EXPECT_EQ(call->Type(), ctor->ReturnType());
     ASSERT_EQ(ctor->Parameters().Length(), 1u);
-    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<sem::Vector>());
+    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<type::Vector>());
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec4F32_Error_ScalarArgumentTypeMismatch) {
@@ -1781,9 +1781,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 4u);
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec4F32_Success_Scalar) {
@@ -1793,9 +1793,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 4u);
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec4F16_Success_Scalar) {
@@ -1807,9 +1807,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F16>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F16>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 4u);
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec4U32_Success_Scalar) {
@@ -1819,9 +1819,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::U32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::U32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 4u);
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec4I32_Success_Scalar) {
@@ -1831,9 +1831,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::I32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::I32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 4u);
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec4Bool_Success_Scalar) {
@@ -1843,9 +1843,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::Bool>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::Bool>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 4u);
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec4_Success_Vec2ScalarScalar) {
@@ -1855,9 +1855,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 4u);
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec4_Success_ScalarVec2Scalar) {
@@ -1867,9 +1867,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 4u);
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec4_Success_ScalarScalarVec2) {
@@ -1879,9 +1879,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 4u);
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec4_Success_Vec2AndVec2) {
@@ -1891,9 +1891,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 4u);
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec4_Success_Vec3AndScalar) {
@@ -1903,9 +1903,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 4u);
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec4_Success_ScalarAndVec3) {
@@ -1915,9 +1915,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 4u);
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec4_Success_Identity) {
@@ -1927,9 +1927,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 4u);
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vec4_Success_Vec4TypeConversion) {
@@ -1939,9 +1939,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 4u);
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, NestedVectorInitializers_InnerError) {
@@ -1961,9 +1961,9 @@
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
     ASSERT_NE(TypeOf(tc), nullptr);
-    ASSERT_TRUE(TypeOf(tc)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(tc)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_EQ(TypeOf(tc)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(tc)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(tc)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_EQ(TypeOf(tc)->As<type::Vector>()->Width(), 4u);
 }
 
 TEST_F(ResolverTypeInitializerValidationTest, Vector_Alias_Argument_Error) {
@@ -2046,21 +2046,21 @@
 
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
-    ASSERT_TRUE(TypeOf(vec2_bool)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec2_i32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec2_u32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec2_f32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec2_f16)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(vec2_bool)->As<sem::Vector>()->type()->Is<type::Bool>());
-    EXPECT_TRUE(TypeOf(vec2_i32)->As<sem::Vector>()->type()->Is<type::I32>());
-    EXPECT_TRUE(TypeOf(vec2_u32)->As<sem::Vector>()->type()->Is<type::U32>());
-    EXPECT_TRUE(TypeOf(vec2_f32)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_TRUE(TypeOf(vec2_f16)->As<sem::Vector>()->type()->Is<type::F16>());
-    EXPECT_EQ(TypeOf(vec2_bool)->As<sem::Vector>()->Width(), 2u);
-    EXPECT_EQ(TypeOf(vec2_i32)->As<sem::Vector>()->Width(), 2u);
-    EXPECT_EQ(TypeOf(vec2_u32)->As<sem::Vector>()->Width(), 2u);
-    EXPECT_EQ(TypeOf(vec2_f32)->As<sem::Vector>()->Width(), 2u);
-    EXPECT_EQ(TypeOf(vec2_f16)->As<sem::Vector>()->Width(), 2u);
+    ASSERT_TRUE(TypeOf(vec2_bool)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec2_i32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec2_u32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec2_f32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec2_f16)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(vec2_bool)->As<type::Vector>()->type()->Is<type::Bool>());
+    EXPECT_TRUE(TypeOf(vec2_i32)->As<type::Vector>()->type()->Is<type::I32>());
+    EXPECT_TRUE(TypeOf(vec2_u32)->As<type::Vector>()->type()->Is<type::U32>());
+    EXPECT_TRUE(TypeOf(vec2_f32)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_TRUE(TypeOf(vec2_f16)->As<type::Vector>()->type()->Is<type::F16>());
+    EXPECT_EQ(TypeOf(vec2_bool)->As<type::Vector>()->Width(), 2u);
+    EXPECT_EQ(TypeOf(vec2_i32)->As<type::Vector>()->Width(), 2u);
+    EXPECT_EQ(TypeOf(vec2_u32)->As<type::Vector>()->Width(), 2u);
+    EXPECT_EQ(TypeOf(vec2_f32)->As<type::Vector>()->Width(), 2u);
+    EXPECT_EQ(TypeOf(vec2_f16)->As<type::Vector>()->Width(), 2u);
     EXPECT_EQ(TypeOf(vec2_bool), TypeOf(vec2_bool->target.type));
     EXPECT_EQ(TypeOf(vec2_i32), TypeOf(vec2_i32->target.type));
     EXPECT_EQ(TypeOf(vec2_u32), TypeOf(vec2_u32->target.type));
@@ -2080,21 +2080,21 @@
 
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
-    ASSERT_TRUE(TypeOf(vec2_bool)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec2_i32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec2_u32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec2_f32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec2_f16)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(vec2_bool)->As<sem::Vector>()->type()->Is<type::Bool>());
-    EXPECT_TRUE(TypeOf(vec2_i32)->As<sem::Vector>()->type()->Is<type::I32>());
-    EXPECT_TRUE(TypeOf(vec2_u32)->As<sem::Vector>()->type()->Is<type::U32>());
-    EXPECT_TRUE(TypeOf(vec2_f32)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_TRUE(TypeOf(vec2_f16)->As<sem::Vector>()->type()->Is<type::F16>());
-    EXPECT_EQ(TypeOf(vec2_bool)->As<sem::Vector>()->Width(), 2u);
-    EXPECT_EQ(TypeOf(vec2_i32)->As<sem::Vector>()->Width(), 2u);
-    EXPECT_EQ(TypeOf(vec2_u32)->As<sem::Vector>()->Width(), 2u);
-    EXPECT_EQ(TypeOf(vec2_f32)->As<sem::Vector>()->Width(), 2u);
-    EXPECT_EQ(TypeOf(vec2_f16)->As<sem::Vector>()->Width(), 2u);
+    ASSERT_TRUE(TypeOf(vec2_bool)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec2_i32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec2_u32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec2_f32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec2_f16)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(vec2_bool)->As<type::Vector>()->type()->Is<type::Bool>());
+    EXPECT_TRUE(TypeOf(vec2_i32)->As<type::Vector>()->type()->Is<type::I32>());
+    EXPECT_TRUE(TypeOf(vec2_u32)->As<type::Vector>()->type()->Is<type::U32>());
+    EXPECT_TRUE(TypeOf(vec2_f32)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_TRUE(TypeOf(vec2_f16)->As<type::Vector>()->type()->Is<type::F16>());
+    EXPECT_EQ(TypeOf(vec2_bool)->As<type::Vector>()->Width(), 2u);
+    EXPECT_EQ(TypeOf(vec2_i32)->As<type::Vector>()->Width(), 2u);
+    EXPECT_EQ(TypeOf(vec2_u32)->As<type::Vector>()->Width(), 2u);
+    EXPECT_EQ(TypeOf(vec2_f32)->As<type::Vector>()->Width(), 2u);
+    EXPECT_EQ(TypeOf(vec2_f16)->As<type::Vector>()->Width(), 2u);
     EXPECT_EQ(TypeOf(vec2_bool), TypeOf(vec2_bool->target.type));
     EXPECT_EQ(TypeOf(vec2_i32), TypeOf(vec2_i32->target.type));
     EXPECT_EQ(TypeOf(vec2_u32), TypeOf(vec2_u32->target.type));
@@ -2115,21 +2115,21 @@
 
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
-    ASSERT_TRUE(TypeOf(vec3_bool)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec3_i32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec3_u32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec3_f32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec3_f16)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(vec3_bool)->As<sem::Vector>()->type()->Is<type::Bool>());
-    EXPECT_TRUE(TypeOf(vec3_i32)->As<sem::Vector>()->type()->Is<type::I32>());
-    EXPECT_TRUE(TypeOf(vec3_u32)->As<sem::Vector>()->type()->Is<type::U32>());
-    EXPECT_TRUE(TypeOf(vec3_f32)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_TRUE(TypeOf(vec3_f16)->As<sem::Vector>()->type()->Is<type::F16>());
-    EXPECT_EQ(TypeOf(vec3_bool)->As<sem::Vector>()->Width(), 3u);
-    EXPECT_EQ(TypeOf(vec3_i32)->As<sem::Vector>()->Width(), 3u);
-    EXPECT_EQ(TypeOf(vec3_u32)->As<sem::Vector>()->Width(), 3u);
-    EXPECT_EQ(TypeOf(vec3_f32)->As<sem::Vector>()->Width(), 3u);
-    EXPECT_EQ(TypeOf(vec3_f16)->As<sem::Vector>()->Width(), 3u);
+    ASSERT_TRUE(TypeOf(vec3_bool)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec3_i32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec3_u32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec3_f32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec3_f16)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(vec3_bool)->As<type::Vector>()->type()->Is<type::Bool>());
+    EXPECT_TRUE(TypeOf(vec3_i32)->As<type::Vector>()->type()->Is<type::I32>());
+    EXPECT_TRUE(TypeOf(vec3_u32)->As<type::Vector>()->type()->Is<type::U32>());
+    EXPECT_TRUE(TypeOf(vec3_f32)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_TRUE(TypeOf(vec3_f16)->As<type::Vector>()->type()->Is<type::F16>());
+    EXPECT_EQ(TypeOf(vec3_bool)->As<type::Vector>()->Width(), 3u);
+    EXPECT_EQ(TypeOf(vec3_i32)->As<type::Vector>()->Width(), 3u);
+    EXPECT_EQ(TypeOf(vec3_u32)->As<type::Vector>()->Width(), 3u);
+    EXPECT_EQ(TypeOf(vec3_f32)->As<type::Vector>()->Width(), 3u);
+    EXPECT_EQ(TypeOf(vec3_f16)->As<type::Vector>()->Width(), 3u);
     EXPECT_EQ(TypeOf(vec3_bool), TypeOf(vec3_bool->target.type));
     EXPECT_EQ(TypeOf(vec3_i32), TypeOf(vec3_i32->target.type));
     EXPECT_EQ(TypeOf(vec3_u32), TypeOf(vec3_u32->target.type));
@@ -2149,21 +2149,21 @@
 
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
-    ASSERT_TRUE(TypeOf(vec3_bool)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec3_i32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec3_u32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec3_f32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec3_f16)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(vec3_bool)->As<sem::Vector>()->type()->Is<type::Bool>());
-    EXPECT_TRUE(TypeOf(vec3_i32)->As<sem::Vector>()->type()->Is<type::I32>());
-    EXPECT_TRUE(TypeOf(vec3_u32)->As<sem::Vector>()->type()->Is<type::U32>());
-    EXPECT_TRUE(TypeOf(vec3_f32)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_TRUE(TypeOf(vec3_f16)->As<sem::Vector>()->type()->Is<type::F16>());
-    EXPECT_EQ(TypeOf(vec3_bool)->As<sem::Vector>()->Width(), 3u);
-    EXPECT_EQ(TypeOf(vec3_i32)->As<sem::Vector>()->Width(), 3u);
-    EXPECT_EQ(TypeOf(vec3_u32)->As<sem::Vector>()->Width(), 3u);
-    EXPECT_EQ(TypeOf(vec3_f32)->As<sem::Vector>()->Width(), 3u);
-    EXPECT_EQ(TypeOf(vec3_f16)->As<sem::Vector>()->Width(), 3u);
+    ASSERT_TRUE(TypeOf(vec3_bool)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec3_i32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec3_u32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec3_f32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec3_f16)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(vec3_bool)->As<type::Vector>()->type()->Is<type::Bool>());
+    EXPECT_TRUE(TypeOf(vec3_i32)->As<type::Vector>()->type()->Is<type::I32>());
+    EXPECT_TRUE(TypeOf(vec3_u32)->As<type::Vector>()->type()->Is<type::U32>());
+    EXPECT_TRUE(TypeOf(vec3_f32)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_TRUE(TypeOf(vec3_f16)->As<type::Vector>()->type()->Is<type::F16>());
+    EXPECT_EQ(TypeOf(vec3_bool)->As<type::Vector>()->Width(), 3u);
+    EXPECT_EQ(TypeOf(vec3_i32)->As<type::Vector>()->Width(), 3u);
+    EXPECT_EQ(TypeOf(vec3_u32)->As<type::Vector>()->Width(), 3u);
+    EXPECT_EQ(TypeOf(vec3_f32)->As<type::Vector>()->Width(), 3u);
+    EXPECT_EQ(TypeOf(vec3_f16)->As<type::Vector>()->Width(), 3u);
     EXPECT_EQ(TypeOf(vec3_bool), TypeOf(vec3_bool->target.type));
     EXPECT_EQ(TypeOf(vec3_i32), TypeOf(vec3_i32->target.type));
     EXPECT_EQ(TypeOf(vec3_u32), TypeOf(vec3_u32->target.type));
@@ -2184,21 +2184,21 @@
 
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
-    ASSERT_TRUE(TypeOf(vec3_bool)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec3_i32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec3_u32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec3_f32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec3_f16)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(vec3_bool)->As<sem::Vector>()->type()->Is<type::Bool>());
-    EXPECT_TRUE(TypeOf(vec3_i32)->As<sem::Vector>()->type()->Is<type::I32>());
-    EXPECT_TRUE(TypeOf(vec3_u32)->As<sem::Vector>()->type()->Is<type::U32>());
-    EXPECT_TRUE(TypeOf(vec3_f32)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_TRUE(TypeOf(vec3_f16)->As<sem::Vector>()->type()->Is<type::F16>());
-    EXPECT_EQ(TypeOf(vec3_bool)->As<sem::Vector>()->Width(), 3u);
-    EXPECT_EQ(TypeOf(vec3_i32)->As<sem::Vector>()->Width(), 3u);
-    EXPECT_EQ(TypeOf(vec3_u32)->As<sem::Vector>()->Width(), 3u);
-    EXPECT_EQ(TypeOf(vec3_f32)->As<sem::Vector>()->Width(), 3u);
-    EXPECT_EQ(TypeOf(vec3_f16)->As<sem::Vector>()->Width(), 3u);
+    ASSERT_TRUE(TypeOf(vec3_bool)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec3_i32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec3_u32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec3_f32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec3_f16)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(vec3_bool)->As<type::Vector>()->type()->Is<type::Bool>());
+    EXPECT_TRUE(TypeOf(vec3_i32)->As<type::Vector>()->type()->Is<type::I32>());
+    EXPECT_TRUE(TypeOf(vec3_u32)->As<type::Vector>()->type()->Is<type::U32>());
+    EXPECT_TRUE(TypeOf(vec3_f32)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_TRUE(TypeOf(vec3_f16)->As<type::Vector>()->type()->Is<type::F16>());
+    EXPECT_EQ(TypeOf(vec3_bool)->As<type::Vector>()->Width(), 3u);
+    EXPECT_EQ(TypeOf(vec3_i32)->As<type::Vector>()->Width(), 3u);
+    EXPECT_EQ(TypeOf(vec3_u32)->As<type::Vector>()->Width(), 3u);
+    EXPECT_EQ(TypeOf(vec3_f32)->As<type::Vector>()->Width(), 3u);
+    EXPECT_EQ(TypeOf(vec3_f16)->As<type::Vector>()->Width(), 3u);
     EXPECT_EQ(TypeOf(vec3_bool), TypeOf(vec3_bool->target.type));
     EXPECT_EQ(TypeOf(vec3_i32), TypeOf(vec3_i32->target.type));
     EXPECT_EQ(TypeOf(vec3_u32), TypeOf(vec3_u32->target.type));
@@ -2223,21 +2223,21 @@
 
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
-    ASSERT_TRUE(TypeOf(vec4_bool)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec4_i32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec4_u32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec4_f32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec4_f16)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(vec4_bool)->As<sem::Vector>()->type()->Is<type::Bool>());
-    EXPECT_TRUE(TypeOf(vec4_i32)->As<sem::Vector>()->type()->Is<type::I32>());
-    EXPECT_TRUE(TypeOf(vec4_u32)->As<sem::Vector>()->type()->Is<type::U32>());
-    EXPECT_TRUE(TypeOf(vec4_f32)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_TRUE(TypeOf(vec4_f16)->As<sem::Vector>()->type()->Is<type::F16>());
-    EXPECT_EQ(TypeOf(vec4_bool)->As<sem::Vector>()->Width(), 4u);
-    EXPECT_EQ(TypeOf(vec4_i32)->As<sem::Vector>()->Width(), 4u);
-    EXPECT_EQ(TypeOf(vec4_u32)->As<sem::Vector>()->Width(), 4u);
-    EXPECT_EQ(TypeOf(vec4_f32)->As<sem::Vector>()->Width(), 4u);
-    EXPECT_EQ(TypeOf(vec4_f16)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(vec4_bool)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec4_i32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec4_u32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec4_f32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec4_f16)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(vec4_bool)->As<type::Vector>()->type()->Is<type::Bool>());
+    EXPECT_TRUE(TypeOf(vec4_i32)->As<type::Vector>()->type()->Is<type::I32>());
+    EXPECT_TRUE(TypeOf(vec4_u32)->As<type::Vector>()->type()->Is<type::U32>());
+    EXPECT_TRUE(TypeOf(vec4_f32)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_TRUE(TypeOf(vec4_f16)->As<type::Vector>()->type()->Is<type::F16>());
+    EXPECT_EQ(TypeOf(vec4_bool)->As<type::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(vec4_i32)->As<type::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(vec4_u32)->As<type::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(vec4_f32)->As<type::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(vec4_f16)->As<type::Vector>()->Width(), 4u);
     EXPECT_EQ(TypeOf(vec4_bool), TypeOf(vec4_bool->target.type));
     EXPECT_EQ(TypeOf(vec4_i32), TypeOf(vec4_i32->target.type));
     EXPECT_EQ(TypeOf(vec4_u32), TypeOf(vec4_u32->target.type));
@@ -2258,21 +2258,21 @@
 
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
-    ASSERT_TRUE(TypeOf(vec4_bool)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec4_i32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec4_u32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec4_f32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec4_f16)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(vec4_bool)->As<sem::Vector>()->type()->Is<type::Bool>());
-    EXPECT_TRUE(TypeOf(vec4_i32)->As<sem::Vector>()->type()->Is<type::I32>());
-    EXPECT_TRUE(TypeOf(vec4_u32)->As<sem::Vector>()->type()->Is<type::U32>());
-    EXPECT_TRUE(TypeOf(vec4_f32)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_TRUE(TypeOf(vec4_f16)->As<sem::Vector>()->type()->Is<type::F16>());
-    EXPECT_EQ(TypeOf(vec4_bool)->As<sem::Vector>()->Width(), 4u);
-    EXPECT_EQ(TypeOf(vec4_i32)->As<sem::Vector>()->Width(), 4u);
-    EXPECT_EQ(TypeOf(vec4_u32)->As<sem::Vector>()->Width(), 4u);
-    EXPECT_EQ(TypeOf(vec4_f32)->As<sem::Vector>()->Width(), 4u);
-    EXPECT_EQ(TypeOf(vec4_f16)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(vec4_bool)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec4_i32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec4_u32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec4_f32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec4_f16)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(vec4_bool)->As<type::Vector>()->type()->Is<type::Bool>());
+    EXPECT_TRUE(TypeOf(vec4_i32)->As<type::Vector>()->type()->Is<type::I32>());
+    EXPECT_TRUE(TypeOf(vec4_u32)->As<type::Vector>()->type()->Is<type::U32>());
+    EXPECT_TRUE(TypeOf(vec4_f32)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_TRUE(TypeOf(vec4_f16)->As<type::Vector>()->type()->Is<type::F16>());
+    EXPECT_EQ(TypeOf(vec4_bool)->As<type::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(vec4_i32)->As<type::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(vec4_u32)->As<type::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(vec4_f32)->As<type::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(vec4_f16)->As<type::Vector>()->Width(), 4u);
     EXPECT_EQ(TypeOf(vec4_bool), TypeOf(vec4_bool->target.type));
     EXPECT_EQ(TypeOf(vec4_i32), TypeOf(vec4_i32->target.type));
     EXPECT_EQ(TypeOf(vec4_u32), TypeOf(vec4_u32->target.type));
@@ -2297,21 +2297,21 @@
 
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
-    ASSERT_TRUE(TypeOf(vec4_bool)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec4_i32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec4_u32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec4_f32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec4_f16)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(vec4_bool)->As<sem::Vector>()->type()->Is<type::Bool>());
-    EXPECT_TRUE(TypeOf(vec4_i32)->As<sem::Vector>()->type()->Is<type::I32>());
-    EXPECT_TRUE(TypeOf(vec4_u32)->As<sem::Vector>()->type()->Is<type::U32>());
-    EXPECT_TRUE(TypeOf(vec4_f32)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_TRUE(TypeOf(vec4_f16)->As<sem::Vector>()->type()->Is<type::F16>());
-    EXPECT_EQ(TypeOf(vec4_bool)->As<sem::Vector>()->Width(), 4u);
-    EXPECT_EQ(TypeOf(vec4_i32)->As<sem::Vector>()->Width(), 4u);
-    EXPECT_EQ(TypeOf(vec4_u32)->As<sem::Vector>()->Width(), 4u);
-    EXPECT_EQ(TypeOf(vec4_f32)->As<sem::Vector>()->Width(), 4u);
-    EXPECT_EQ(TypeOf(vec4_f16)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(vec4_bool)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec4_i32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec4_u32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec4_f32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec4_f16)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(vec4_bool)->As<type::Vector>()->type()->Is<type::Bool>());
+    EXPECT_TRUE(TypeOf(vec4_i32)->As<type::Vector>()->type()->Is<type::I32>());
+    EXPECT_TRUE(TypeOf(vec4_u32)->As<type::Vector>()->type()->Is<type::U32>());
+    EXPECT_TRUE(TypeOf(vec4_f32)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_TRUE(TypeOf(vec4_f16)->As<type::Vector>()->type()->Is<type::F16>());
+    EXPECT_EQ(TypeOf(vec4_bool)->As<type::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(vec4_i32)->As<type::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(vec4_u32)->As<type::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(vec4_f32)->As<type::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(vec4_f16)->As<type::Vector>()->Width(), 4u);
     EXPECT_EQ(TypeOf(vec4_bool), TypeOf(vec4_bool->target.type));
     EXPECT_EQ(TypeOf(vec4_i32), TypeOf(vec4_i32->target.type));
     EXPECT_EQ(TypeOf(vec4_u32), TypeOf(vec4_u32->target.type));
@@ -2336,21 +2336,21 @@
 
     ASSERT_TRUE(r()->Resolve()) << r()->error();
 
-    ASSERT_TRUE(TypeOf(vec4_bool)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec4_i32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec4_u32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec4_f32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(vec4_f16)->Is<sem::Vector>());
-    EXPECT_TRUE(TypeOf(vec4_bool)->As<sem::Vector>()->type()->Is<type::Bool>());
-    EXPECT_TRUE(TypeOf(vec4_i32)->As<sem::Vector>()->type()->Is<type::I32>());
-    EXPECT_TRUE(TypeOf(vec4_u32)->As<sem::Vector>()->type()->Is<type::U32>());
-    EXPECT_TRUE(TypeOf(vec4_f32)->As<sem::Vector>()->type()->Is<type::F32>());
-    EXPECT_TRUE(TypeOf(vec4_f16)->As<sem::Vector>()->type()->Is<type::F16>());
-    EXPECT_EQ(TypeOf(vec4_bool)->As<sem::Vector>()->Width(), 4u);
-    EXPECT_EQ(TypeOf(vec4_i32)->As<sem::Vector>()->Width(), 4u);
-    EXPECT_EQ(TypeOf(vec4_u32)->As<sem::Vector>()->Width(), 4u);
-    EXPECT_EQ(TypeOf(vec4_f32)->As<sem::Vector>()->Width(), 4u);
-    EXPECT_EQ(TypeOf(vec4_f16)->As<sem::Vector>()->Width(), 4u);
+    ASSERT_TRUE(TypeOf(vec4_bool)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec4_i32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec4_u32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec4_f32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(vec4_f16)->Is<type::Vector>());
+    EXPECT_TRUE(TypeOf(vec4_bool)->As<type::Vector>()->type()->Is<type::Bool>());
+    EXPECT_TRUE(TypeOf(vec4_i32)->As<type::Vector>()->type()->Is<type::I32>());
+    EXPECT_TRUE(TypeOf(vec4_u32)->As<type::Vector>()->type()->Is<type::U32>());
+    EXPECT_TRUE(TypeOf(vec4_f32)->As<type::Vector>()->type()->Is<type::F32>());
+    EXPECT_TRUE(TypeOf(vec4_f16)->As<type::Vector>()->type()->Is<type::F16>());
+    EXPECT_EQ(TypeOf(vec4_bool)->As<type::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(vec4_i32)->As<type::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(vec4_u32)->As<type::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(vec4_f32)->As<type::Vector>()->Width(), 4u);
+    EXPECT_EQ(TypeOf(vec4_f16)->As<type::Vector>()->Width(), 4u);
     EXPECT_EQ(TypeOf(vec4_bool), TypeOf(vec4_bool->target.type));
     EXPECT_EQ(TypeOf(vec4_i32), TypeOf(vec4_i32->target.type));
     EXPECT_EQ(TypeOf(vec4_u32), TypeOf(vec4_u32->target.type));
diff --git a/src/tint/resolver/validator.cc b/src/tint/resolver/validator.cc
index ec4f4f6..06e0b64 100644
--- a/src/tint/resolver/validator.cc
+++ b/src/tint/resolver/validator.cc
@@ -183,15 +183,15 @@
 // https://gpuweb.github.io/gpuweb/wgsl/#plain-types-section
 bool Validator::IsPlain(const type::Type* type) const {
     return type->is_scalar() ||
-           type->IsAnyOf<sem::Atomic, sem::Vector, sem::Matrix, sem::Array, sem::Struct>();
+           type->IsAnyOf<sem::Atomic, type::Vector, type::Matrix, sem::Array, sem::Struct>();
 }
 
 // https://gpuweb.github.io/gpuweb/wgsl/#fixed-footprint-types
 bool Validator::IsFixedFootprint(const type::Type* type) const {
     return Switch(
-        type,                                      //
-        [&](const sem::Vector*) { return true; },  //
-        [&](const sem::Matrix*) { return true; },  //
+        type,                                       //
+        [&](const type::Vector*) { return true; },  //
+        [&](const type::Matrix*) { return true; },  //
         [&](const sem::Atomic*) { return true; },
         [&](const sem::Array* arr) {
             return !arr->Count()->Is<type::RuntimeArrayCount>() &&
@@ -215,8 +215,8 @@
     }
     return Switch(
         type,  //
-        [&](const sem::Vector* vec) { return IsHostShareable(vec->type()); },
-        [&](const sem::Matrix* mat) { return IsHostShareable(mat->type()); },
+        [&](const type::Vector* vec) { return IsHostShareable(vec->type()); },
+        [&](const type::Matrix* mat) { return IsHostShareable(mat->type()); },
         [&](const sem::Array* arr) { return IsHostShareable(arr->ElemType()); },
         [&](const sem::Struct* str) {
             for (auto* member : str->Members()) {
@@ -522,7 +522,7 @@
                 std::string hint;
                 if (arr->ElemType()->is_scalar()) {
                     hint = "Consider using a vector or struct as the element type instead.";
-                } else if (auto* vec = arr->ElemType()->As<sem::Vector>();
+                } else if (auto* vec = arr->ElemType()->As<type::Vector>();
                            vec && vec->type()->Size() == 4) {
                     hint = "Consider using a vec4 instead.";
                 } else if (arr->ElemType()->Is<sem::Struct>()) {
@@ -857,7 +857,7 @@
                   (is_output && stage == ast::PipelineStage::kVertex))) {
                 is_stage_mismatch = true;
             }
-            if (!(type->is_float_vector() && type->As<sem::Vector>()->Width() == 4)) {
+            if (!(type->is_float_vector() && type->As<type::Vector>()->Width() == 4)) {
                 AddError("store type of " + attr_to_str(attr) + " must be 'vec4<f32>'",
                          attr->source);
                 return false;
@@ -871,7 +871,7 @@
                 !(stage == ast::PipelineStage::kCompute && is_input)) {
                 is_stage_mismatch = true;
             }
-            if (!(type->is_unsigned_integer_vector() && type->As<sem::Vector>()->Width() == 3)) {
+            if (!(type->is_unsigned_integer_vector() && type->As<type::Vector>()->Width() == 3)) {
                 AddError("store type of " + attr_to_str(attr) + " must be 'vec3<u32>'",
                          attr->source);
                 return false;
@@ -1371,7 +1371,7 @@
     }
 
     auto width = [&](const type::Type* ty) {
-        if (auto* vec = ty->As<sem::Vector>()) {
+        if (auto* vec = ty->As<type::Vector>()) {
             return vec->Width();
         }
         return 1u;
@@ -1566,7 +1566,7 @@
         std::string name = sem::str(usage);
         auto* arg = call->Arguments()[index];
         if (auto values = arg->ConstantValue()) {
-            if (auto* vector = values->Type()->As<sem::Vector>()) {
+            if (auto* vector = values->Type()->As<type::Vector>()) {
                 for (size_t i = 0; i < vector->Width(); i++) {
                     auto value = values->Index(i)->As<AInt>();
                     if (value < min || value > max) {
@@ -1790,7 +1790,7 @@
     return true;
 }
 
-bool Validator::Vector(const sem::Vector* ty, const Source& source) const {
+bool Validator::Vector(const type::Vector* ty, const Source& source) const {
     if (!ty->type()->is_scalar()) {
         AddError("vector element type must be 'bool', 'f32', 'f16', 'i32' or 'u32'", source);
         return false;
@@ -1798,7 +1798,7 @@
     return true;
 }
 
-bool Validator::Matrix(const sem::Matrix* ty, const Source& source) const {
+bool Validator::Matrix(const type::Matrix* ty, const Source& source) const {
     if (!ty->is_float_matrix()) {
         AddError("matrix element type must be 'f32' or 'f16'", source);
         return false;
@@ -2409,7 +2409,7 @@
 }
 
 std::string Validator::VectorPretty(uint32_t size, const type::Type* element_type) const {
-    sem::Vector vec_type(element_type, size);
+    type::Vector vec_type(element_type, size);
     return vec_type.FriendlyName(symbols_);
 }
 
diff --git a/src/tint/resolver/validator.h b/src/tint/resolver/validator.h
index 14b1ab2..bed1c15 100644
--- a/src/tint/resolver/validator.h
+++ b/src/tint/resolver/validator.h
@@ -328,7 +328,7 @@
     /// @param ty the matrix to validate
     /// @param source the source of the matrix
     /// @returns true on success, false otherwise
-    bool Matrix(const sem::Matrix* ty, const Source& source) const;
+    bool Matrix(const type::Matrix* ty, const Source& source) const;
 
     /// Validates a function parameter
     /// @param func the function the variable is for
@@ -424,7 +424,7 @@
     /// @param ty the vector to validate
     /// @param source the source of the vector
     /// @returns true on success, false otherwise
-    bool Vector(const sem::Vector* ty, const Source& source) const;
+    bool Vector(const type::Vector* ty, const Source& source) const;
 
     /// Validates an array initializer
     /// @param ctor the call expresion to validate
diff --git a/src/tint/resolver/validator_is_storeable_test.cc b/src/tint/resolver/validator_is_storeable_test.cc
index 7e4a5ba..81299f1 100644
--- a/src/tint/resolver/validator_is_storeable_test.cc
+++ b/src/tint/resolver/validator_is_storeable_test.cc
@@ -36,45 +36,45 @@
 }
 
 TEST_F(ValidatorIsStorableTest, Vector) {
-    EXPECT_TRUE(v()->IsStorable(create<sem::Vector>(create<type::I32>(), 2u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Vector>(create<type::I32>(), 3u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Vector>(create<type::I32>(), 4u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Vector>(create<type::U32>(), 2u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Vector>(create<type::U32>(), 3u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Vector>(create<type::U32>(), 4u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Vector>(create<type::F32>(), 2u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Vector>(create<type::F32>(), 3u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Vector>(create<type::F32>(), 4u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Vector>(create<type::F16>(), 2u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Vector>(create<type::F16>(), 3u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Vector>(create<type::F16>(), 4u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Vector>(create<type::I32>(), 2u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Vector>(create<type::I32>(), 3u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Vector>(create<type::I32>(), 4u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Vector>(create<type::U32>(), 2u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Vector>(create<type::U32>(), 3u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Vector>(create<type::U32>(), 4u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Vector>(create<type::F32>(), 2u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Vector>(create<type::F32>(), 3u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Vector>(create<type::F32>(), 4u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Vector>(create<type::F16>(), 2u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Vector>(create<type::F16>(), 3u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Vector>(create<type::F16>(), 4u)));
 }
 
 TEST_F(ValidatorIsStorableTest, Matrix) {
-    auto* vec2_f32 = create<sem::Vector>(create<type::F32>(), 2u);
-    auto* vec3_f32 = create<sem::Vector>(create<type::F32>(), 3u);
-    auto* vec4_f32 = create<sem::Vector>(create<type::F32>(), 4u);
-    auto* vec2_f16 = create<sem::Vector>(create<type::F16>(), 2u);
-    auto* vec3_f16 = create<sem::Vector>(create<type::F16>(), 3u);
-    auto* vec4_f16 = create<sem::Vector>(create<type::F16>(), 4u);
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec2_f32, 2u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec2_f32, 3u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec2_f32, 4u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec3_f32, 2u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec3_f32, 3u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec3_f32, 4u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec4_f32, 2u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec4_f32, 3u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec4_f32, 4u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec2_f16, 2u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec2_f16, 3u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec2_f16, 4u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec3_f16, 2u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec3_f16, 3u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec3_f16, 4u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec4_f16, 2u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec4_f16, 3u)));
-    EXPECT_TRUE(v()->IsStorable(create<sem::Matrix>(vec4_f16, 4u)));
+    auto* vec2_f32 = create<type::Vector>(create<type::F32>(), 2u);
+    auto* vec3_f32 = create<type::Vector>(create<type::F32>(), 3u);
+    auto* vec4_f32 = create<type::Vector>(create<type::F32>(), 4u);
+    auto* vec2_f16 = create<type::Vector>(create<type::F16>(), 2u);
+    auto* vec3_f16 = create<type::Vector>(create<type::F16>(), 3u);
+    auto* vec4_f16 = create<type::Vector>(create<type::F16>(), 4u);
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec2_f32, 2u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec2_f32, 3u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec2_f32, 4u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec3_f32, 2u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec3_f32, 3u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec3_f32, 4u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec4_f32, 2u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec4_f32, 3u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec4_f32, 4u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec2_f16, 2u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec2_f16, 3u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec2_f16, 4u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec3_f16, 2u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec3_f16, 3u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec3_f16, 4u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec4_f16, 2u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec4_f16, 3u)));
+    EXPECT_TRUE(v()->IsStorable(create<type::Matrix>(vec4_f16, 4u)));
 }
 
 TEST_F(ValidatorIsStorableTest, Pointer) {
diff --git a/src/tint/resolver/variable_test.cc b/src/tint/resolver/variable_test.cc
index 16491c0..ad3420e 100644
--- a/src/tint/resolver/variable_test.cc
+++ b/src/tint/resolver/variable_test.cc
@@ -916,10 +916,10 @@
     ASSERT_TRUE(TypeOf(c_i32)->Is<type::I32>());
     ASSERT_TRUE(TypeOf(c_u32)->Is<type::U32>());
     ASSERT_TRUE(TypeOf(c_f32)->Is<type::F32>());
-    ASSERT_TRUE(TypeOf(c_vi32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(c_vu32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(c_vf32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(c_mf32)->Is<sem::Matrix>());
+    ASSERT_TRUE(TypeOf(c_vi32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(c_vu32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(c_vf32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(c_mf32)->Is<type::Matrix>());
     ASSERT_TRUE(TypeOf(c_s)->Is<sem::Struct>());
 
     EXPECT_TRUE(Sem().Get(c_i32)->ConstantValue()->AllZero());
@@ -976,13 +976,13 @@
     ASSERT_TRUE(TypeOf(c_f32)->Is<type::F32>());
     ASSERT_TRUE(TypeOf(c_ai)->Is<type::AbstractInt>());
     ASSERT_TRUE(TypeOf(c_af)->Is<type::AbstractFloat>());
-    ASSERT_TRUE(TypeOf(c_vi32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(c_vu32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(c_vf32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(c_vai)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(c_vaf)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(c_mf32)->Is<sem::Matrix>());
-    ASSERT_TRUE(TypeOf(c_maf32)->Is<sem::Matrix>());
+    ASSERT_TRUE(TypeOf(c_vi32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(c_vu32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(c_vf32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(c_vai)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(c_vaf)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(c_mf32)->Is<type::Matrix>());
+    ASSERT_TRUE(TypeOf(c_maf32)->Is<type::Matrix>());
     ASSERT_TRUE(TypeOf(c_s)->Is<sem::Struct>());
 
     EXPECT_TRUE(Sem().Get(c_i32)->ConstantValue()->AllZero());
@@ -1096,10 +1096,10 @@
     ASSERT_TRUE(TypeOf(c_i32)->Is<type::I32>());
     ASSERT_TRUE(TypeOf(c_u32)->Is<type::U32>());
     ASSERT_TRUE(TypeOf(c_f32)->Is<type::F32>());
-    ASSERT_TRUE(TypeOf(c_vi32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(c_vu32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(c_vf32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(c_mf32)->Is<sem::Matrix>());
+    ASSERT_TRUE(TypeOf(c_vi32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(c_vu32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(c_vf32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(c_mf32)->Is<type::Matrix>());
 
     EXPECT_TRUE(Sem().Get(c_i32)->ConstantValue()->AllZero());
     EXPECT_TRUE(Sem().Get(c_u32)->ConstantValue()->AllZero());
@@ -1147,13 +1147,13 @@
     ASSERT_TRUE(TypeOf(c_f32)->Is<type::F32>());
     ASSERT_TRUE(TypeOf(c_ai)->Is<type::AbstractInt>());
     ASSERT_TRUE(TypeOf(c_af)->Is<type::AbstractFloat>());
-    ASSERT_TRUE(TypeOf(c_vi32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(c_vu32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(c_vf32)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(c_vai)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(c_vaf)->Is<sem::Vector>());
-    ASSERT_TRUE(TypeOf(c_mf32)->Is<sem::Matrix>());
-    ASSERT_TRUE(TypeOf(c_maf32)->Is<sem::Matrix>());
+    ASSERT_TRUE(TypeOf(c_vi32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(c_vu32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(c_vf32)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(c_vai)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(c_vaf)->Is<type::Vector>());
+    ASSERT_TRUE(TypeOf(c_mf32)->Is<type::Matrix>());
+    ASSERT_TRUE(TypeOf(c_maf32)->Is<type::Matrix>());
 
     EXPECT_TRUE(Sem().Get(c_i32)->ConstantValue()->AllZero());
     EXPECT_TRUE(Sem().Get(c_u32)->ConstantValue()->AllZero());
diff --git a/src/tint/tint.natvis b/src/tint/tint.natvis
index 4d2c3a3..2296189 100644
--- a/src/tint/tint.natvis
+++ b/src/tint/tint.natvis
@@ -252,7 +252,7 @@
 		<DisplayString>f32</DisplayString>
 	</Type>
 
-	<Type Name="tint::sem::Vector">
+	<Type Name="tint::type::Vector">
 		<DisplayString>vec{width_}&lt;{*subtype_}&gt;</DisplayString>
 	</Type>
 
diff --git a/src/tint/transform/builtin_polyfill.cc b/src/tint/transform/builtin_polyfill.cc
index 3a3c070..5ae0830 100644
--- a/src/tint/transform/builtin_polyfill.cc
+++ b/src/tint/transform/builtin_polyfill.cc
@@ -487,7 +487,7 @@
             if (!ty->is_unsigned_integer_scalar_or_vector()) {
                 expr = b.Construct<i32>(expr);
             }
-            if (ty->Is<sem::Vector>()) {
+            if (ty->Is<type::Vector>()) {
                 expr = b.Construct(T(ty), expr);
             }
             return expr;
@@ -643,7 +643,7 @@
     /// with scalar calls.
     /// @param vec the vector type
     /// @return the polyfill function name
-    Symbol quantizeToF16(const sem::Vector* vec) {
+    Symbol quantizeToF16(const type::Vector* vec) {
         auto name = b.Symbols().New("tint_quantizeToF16");
         utils::Vector<const ast::Expression*, 4> args;
         for (uint32_t i = 0; i < vec->Width(); i++) {
@@ -673,7 +673,7 @@
         auto* rhs_ty = ctx.src->TypeOf(bin_op->rhs)->UnwrapRef();
         auto* lhs_el_ty = type::Type::DeepestElementOf(lhs_ty);
         const ast::Expression* mask = b.Expr(AInt(lhs_el_ty->Size() * 8 - 1));
-        if (rhs_ty->Is<sem::Vector>()) {
+        if (rhs_ty->Is<type::Vector>()) {
             mask = b.Construct(CreateASTTypeFor(ctx, rhs_ty), mask);
         }
         auto* lhs = ctx.Clone(bin_op->lhs);
@@ -761,7 +761,7 @@
 
     /// @returns 1 if `ty` is not a vector, otherwise the vector width
     uint32_t WidthOf(const type::Type* ty) const {
-        if (auto* v = ty->As<sem::Vector>()) {
+        if (auto* v = ty->As<type::Vector>()) {
             return v->Width();
         }
         return 1;
@@ -905,7 +905,7 @@
                     break;
                 case sem::BuiltinType::kQuantizeToF16:
                     if (polyfill.quantize_to_vec_f16) {
-                        if (auto* vec = builtin->ReturnType()->As<sem::Vector>()) {
+                        if (auto* vec = builtin->ReturnType()->As<type::Vector>()) {
                             fn = builtin_polyfills.GetOrCreate(
                                 builtin, [&] { return s.quantizeToF16(vec); });
                         }
diff --git a/src/tint/transform/decompose_memory_access.cc b/src/tint/transform/decompose_memory_access.cc
index 4c5eda4..832fb05 100644
--- a/src/tint/transform/decompose_memory_access.cc
+++ b/src/tint/transform/decompose_memory_access.cc
@@ -157,7 +157,7 @@
         out = DecomposeMemoryAccess::Intrinsic::DataType::kF16;
         return true;
     }
-    if (auto* vec = ty->As<sem::Vector>()) {
+    if (auto* vec = ty->As<type::Vector>()) {
         switch (vec->Width()) {
             case 2:
                 if (vec->type()->Is<type::I32>()) {
@@ -529,7 +529,7 @@
                            });
                 } else {
                     utils::Vector<const ast::Expression*, 8> values;
-                    if (auto* mat_ty = el_ty->As<sem::Matrix>()) {
+                    if (auto* mat_ty = el_ty->As<type::Matrix>()) {
                         auto* vec_ty = mat_ty->ColumnType();
                         Symbol load = LoadFunc(buf_ty, vec_ty, var_user);
                         for (uint32_t i = 0; i < mat_ty->columns(); i++) {
@@ -629,7 +629,7 @@
 
                             return utils::Vector{b.Decl(array), for_loop};
                         },
-                        [&](const sem::Matrix* mat_ty) {
+                        [&](const type::Matrix* mat_ty) {
                             auto* vec_ty = mat_ty->ColumnType();
                             Symbol store = StoreFunc(buf_ty, vec_ty, var_user);
                             utils::Vector<const ast::Statement*, 4> stmts;
@@ -901,7 +901,7 @@
             if (auto* swizzle = accessor_sem->As<sem::Swizzle>()) {
                 if (swizzle->Indices().Length() == 1) {
                     if (auto access = state.TakeAccess(accessor->structure)) {
-                        auto* vec_ty = access.type->As<sem::Vector>();
+                        auto* vec_ty = access.type->As<type::Vector>();
                         auto* offset = state.Mul(vec_ty->type()->Size(), swizzle->Indices()[0u]);
                         state.AddAccess(accessor, {
                                                       access.var,
@@ -937,7 +937,7 @@
                                               });
                     continue;
                 }
-                if (auto* vec_ty = access.type->As<sem::Vector>()) {
+                if (auto* vec_ty = access.type->As<type::Vector>()) {
                     auto* offset = state.Mul(vec_ty->type()->Size(), accessor->index);
                     state.AddAccess(accessor, {
                                                   access.var,
@@ -946,7 +946,7 @@
                                               });
                     continue;
                 }
-                if (auto* mat_ty = access.type->As<sem::Matrix>()) {
+                if (auto* mat_ty = access.type->As<type::Matrix>()) {
                     auto* offset = state.Mul(mat_ty->ColumnStride(), accessor->index);
                     state.AddAccess(accessor, {
                                                   access.var,
diff --git a/src/tint/transform/decompose_strided_matrix.cc b/src/tint/transform/decompose_strided_matrix.cc
index b7fd7c2..a874e4e 100644
--- a/src/tint/transform/decompose_strided_matrix.cc
+++ b/src/tint/transform/decompose_strided_matrix.cc
@@ -35,7 +35,7 @@
     /// The stride in bytes between columns of the matrix
     uint32_t stride = 0;
     /// The type of the matrix
-    const sem::Matrix* matrix = nullptr;
+    const type::Matrix* matrix = nullptr;
 
     /// @returns a new ast::Array that holds an vector column for each row of the
     /// matrix.
@@ -77,7 +77,7 @@
                 continue;
             }
             for (auto* member : str_ty->Members()) {
-                auto* matrix = member->Type()->As<sem::Matrix>();
+                auto* matrix = member->Type()->As<type::Matrix>();
                 if (!matrix) {
                     continue;
                 }
diff --git a/src/tint/transform/expand_compound_assignment.cc b/src/tint/transform/expand_compound_assignment.cc
index 9fa81dd..3d62f23 100644
--- a/src/tint/transform/expand_compound_assignment.cc
+++ b/src/tint/transform/expand_compound_assignment.cc
@@ -86,7 +86,7 @@
 
         // Helper function that returns `true` if the type of `expr` is a vector.
         auto is_vec = [&](const ast::Expression* expr) {
-            return ctx.src->Sem().Get(expr)->Type()->UnwrapRef()->Is<sem::Vector>();
+            return ctx.src->Sem().Get(expr)->Type()->UnwrapRef()->Is<type::Vector>();
         };
 
         // Hoist the LHS expression subtree into local constants to produce a new
diff --git a/src/tint/transform/module_scope_var_to_entry_point_param.cc b/src/tint/transform/module_scope_var_to_entry_point_param.cc
index 12c1182..288b8f1 100644
--- a/src/tint/transform/module_scope_var_to_entry_point_param.cc
+++ b/src/tint/transform/module_scope_var_to_entry_point_param.cc
@@ -50,7 +50,7 @@
 // Returns `true` if `type` is or contains a matrix type.
 bool ContainsMatrix(const type::Type* type) {
     type = type->UnwrapRef();
-    if (type->Is<sem::Matrix>()) {
+    if (type->Is<type::Matrix>()) {
         return true;
     } else if (auto* ary = type->As<sem::Array>()) {
         return ContainsMatrix(ary->ElemType());
diff --git a/src/tint/transform/packed_vec3.cc b/src/tint/transform/packed_vec3.cc
index af0c219..5b5fdf4 100644
--- a/src/tint/transform/packed_vec3.cc
+++ b/src/tint/transform/packed_vec3.cc
@@ -51,7 +51,7 @@
             if (auto* str = sem.Get<sem::Struct>(decl)) {
                 if (str->IsHostShareable()) {
                     for (auto* member : str->Members()) {
-                        if (auto* vec = member->Type()->As<sem::Vector>()) {
+                        if (auto* vec = member->Type()->As<type::Vector>()) {
                             if (vec->Width() == 3) {
                                 members.Add(member);
 
@@ -121,11 +121,11 @@
         }
 
         // Wrap the load expressions with a cast to the unpacked type.
-        utils::Hashmap<const sem::Vector*, Symbol, 3> unpack_fns;
+        utils::Hashmap<const type::Vector*, Symbol, 3> unpack_fns;
         for (auto* ref : refs) {
             // ref is either a packed vec3 that needs casting, or a pointer to a vec3 which we just
             // leave alone.
-            if (auto* vec_ty = ref->Type()->UnwrapRef()->As<sem::Vector>()) {
+            if (auto* vec_ty = ref->Type()->UnwrapRef()->As<type::Vector>()) {
                 auto* expr = ref->Declaration();
                 ctx.Replace(expr, [this, vec_ty, expr] {  //
                     auto* packed = ctx.CloneWithoutTransform(expr);
diff --git a/src/tint/transform/robustness.cc b/src/tint/transform/robustness.cc
index 93edec1..34fb105 100644
--- a/src/tint/transform/robustness.cc
+++ b/src/tint/transform/robustness.cc
@@ -86,7 +86,7 @@
 
         auto* clamped_idx = Switch(
             sem->Object()->Type()->UnwrapRef(),  //
-            [&](const sem::Vector* vec) -> const ast::Expression* {
+            [&](const type::Vector* vec) -> const ast::Expression* {
                 if (sem->Index()->ConstantValue()) {
                     // Index and size is constant.
                     // Validation will have rejected any OOB accesses.
@@ -95,7 +95,7 @@
 
                 return b.Call("min", idx(), u32(vec->Width() - 1u));
             },
-            [&](const sem::Matrix* mat) -> const ast::Expression* {
+            [&](const type::Matrix* mat) -> const ast::Expression* {
                 if (sem->Index()->ConstantValue()) {
                     // Index and size is constant.
                     // Validation will have rejected any OOB accesses.
@@ -177,7 +177,7 @@
         auto* coords_ty = builtin->Parameters()[static_cast<size_t>(coords_idx)]->Type();
 
         auto width_of = [&](const type::Type* ty) {
-            if (auto* vec = ty->As<sem::Vector>()) {
+            if (auto* vec = ty->As<type::Vector>()) {
                 return vec->Width();
             }
             return 1u;
diff --git a/src/tint/transform/std140.cc b/src/tint/transform/std140.cc
index d2e9349..d466a7c 100644
--- a/src/tint/transform/std140.cc
+++ b/src/tint/transform/std140.cc
@@ -132,7 +132,7 @@
             while (auto* arr = ty->As<sem::Array>()) {
                 ty = arr->ElemType();
             }
-            if (auto* mat = ty->As<sem::Matrix>()) {
+            if (auto* mat = ty->As<type::Matrix>()) {
                 if (MatrixNeedsDecomposing(mat)) {
                     return true;
                 }
@@ -241,7 +241,7 @@
     };
 
     // Map of matrix type in src, to decomposed column structure in ctx.dst.
-    utils::Hashmap<const sem::Matrix*, Std140Matrix, 8> std140_mats;
+    utils::Hashmap<const type::Matrix*, Std140Matrix, 8> std140_mats;
 
     /// AccessChain describes a chain of access expressions to uniform buffer variable.
     struct AccessChain {
@@ -253,7 +253,7 @@
         utils::Vector<const sem::Expression*, 8> dynamic_indices;
         /// The type of the std140-decomposed matrix being accessed.
         /// May be nullptr if the chain does not pass through a std140-decomposed matrix.
-        const sem::Matrix* std140_mat_ty = nullptr;
+        const type::Matrix* std140_mat_ty = nullptr;
         /// The index in #indices of the access that resolves to the std140-decomposed matrix.
         /// May hold no value if the chain does not pass through a std140-decomposed matrix.
         std::optional<size_t> std140_mat_idx;
@@ -266,7 +266,9 @@
 
     /// @returns true if the given matrix needs decomposing to column vectors for std140 layout.
     /// Std140 layout require matrix stride to be 16, otherwise decomposing is needed.
-    static bool MatrixNeedsDecomposing(const sem::Matrix* mat) { return mat->ColumnStride() != 16; }
+    static bool MatrixNeedsDecomposing(const type::Matrix* mat) {
+        return mat->ColumnStride() != 16;
+    }
 
     /// ForkTypes walks the user-declared types in dependency order, forking structures that are
     /// used as uniform buffers which (transitively) use matrices that need std140 decomposition to
@@ -282,7 +284,7 @@
                 bool fork_std140 = false;
                 utils::Vector<const ast::StructMember*, 8> members;
                 for (auto* member : str->Members()) {
-                    if (auto* mat = member->Type()->As<sem::Matrix>()) {
+                    if (auto* mat = member->Type()->As<type::Matrix>()) {
                         // Is this member a matrix that needs decomposition for std140-layout?
                         if (MatrixNeedsDecomposing(mat)) {
                             // Structure member of matrix type needs decomposition.
@@ -406,7 +408,7 @@
                 }
                 return nullptr;
             },
-            [&](const sem::Matrix* mat) -> const ast::Type* {
+            [&](const type::Matrix* mat) -> const ast::Type* {
                 if (MatrixNeedsDecomposing(mat)) {
                     auto std140_mat = std140_mats.GetOrCreate(mat, [&] {
                         auto name = b.Symbols().New("mat" + std::to_string(mat->columns()) + "x" +
@@ -453,7 +455,7 @@
     /// @param size the size in bytes of the matrix.
     /// @returns a vector of decomposed matrix column vectors as structure members (in ctx.dst).
     utils::Vector<const ast::StructMember*, 4> DecomposedMatrixStructMembers(
-        const sem::Matrix* mat,
+        const type::Matrix* mat,
         const std::string& name_prefix,
         uint32_t align,
         uint32_t size) {
@@ -533,7 +535,7 @@
                     if (std140_mat_members.Contains(a->Member())) {
                         // Record this on the access.
                         access.std140_mat_idx = access.indices.Length();
-                        access.std140_mat_ty = expr->Type()->UnwrapRef()->As<sem::Matrix>();
+                        access.std140_mat_ty = expr->Type()->UnwrapRef()->As<type::Matrix>();
                     }
                     // Structure member accesses are always statically indexed
                     access.indices.Push(u32(a->Member()->Index()));
@@ -551,7 +553,7 @@
                     expr = a->Object();
 
                     // Is the object a std140 decomposed matrix?
-                    if (auto* mat = expr->Type()->UnwrapRef()->As<sem::Matrix>()) {
+                    if (auto* mat = expr->Type()->UnwrapRef()->As<type::Matrix>()) {
                         if (std140_mats.Contains(mat)) {
                             // Record this on the access.
                             access.std140_mat_idx = access.indices.Length();
@@ -641,7 +643,7 @@
                 }
                 return "arr" + std::to_string(count.value()) + "_" + ConvertSuffix(arr->ElemType());
             },
-            [&](const sem::Matrix* mat) {
+            [&](const type::Matrix* mat) {
                 return "mat" + std::to_string(mat->columns()) + "x" + std::to_string(mat->rows()) +
                        "_" + ConvertSuffix(mat->type());
             },
@@ -713,7 +715,7 @@
                     }
                     stmts.Push(b.Return(b.Construct(CreateASTTypeFor(ctx, ty), std::move(args))));
                 },  //
-                [&](const sem::Matrix* mat) {
+                [&](const type::Matrix* mat) {
                     // Reassemble a std140 matrix from the structure of column vector members.
                     if (auto std140_mat = std140_mats.Get(mat)) {
                         utils::Vector<const ast::Expression*, 8> args;
@@ -835,7 +837,7 @@
             auto* mat_member = str->Members()[mat_member_idx];
             auto mat_columns = *std140_mat_members.Get(mat_member);
             expr = b.MemberAccessor(expr, mat_columns[column_idx]->symbol);
-            ty = mat_member->Type()->As<sem::Matrix>()->ColumnType();
+            ty = mat_member->Type()->As<type::Matrix>()->ColumnType();
         } else {
             // Non-structure-member matrix. The columns are decomposed into a new, bespoke std140
             // structure.
@@ -843,8 +845,8 @@
                 BuildAccessExpr(expr, ty, chain, std140_mat_idx, dynamic_index);
             expr = new_expr;
             ty = new_ty;
-            auto* mat = ty->As<sem::Matrix>();
-            auto std140_mat = std140_mats.Get(ty->As<sem::Matrix>());
+            auto* mat = ty->As<type::Matrix>();
+            auto std140_mat = std140_mats.Get(ty->As<type::Matrix>());
             expr = b.MemberAccessor(expr, std140_mat->columns[column_idx]);
             ty = mat->ColumnType();
         }
@@ -918,7 +920,7 @@
                 }
                 auto mat_columns = *std140_mat_members.Get(mat_member);
                 expr = b.MemberAccessor(expr, mat_columns[column_idx]->symbol);
-                ty = mat_member->Type()->As<sem::Matrix>()->ColumnType();
+                ty = mat_member->Type()->As<type::Matrix>()->ColumnType();
             } else {
                 // Non-structure-member matrix. The columns are decomposed into a new, bespoke
                 // std140 structure.
@@ -929,8 +931,8 @@
                 if (column_idx == 0) {
                     name += "_" + mat_name + "_p" + std::to_string(column_param_idx);
                 }
-                auto* mat = ty->As<sem::Matrix>();
-                auto std140_mat = std140_mats.Get(ty->As<sem::Matrix>());
+                auto* mat = ty->As<type::Matrix>();
+                auto std140_mat = std140_mats.Get(ty->As<type::Matrix>());
                 expr = b.MemberAccessor(expr, std140_mat->columns[column_idx]);
                 ty = mat->ColumnType();
             }
@@ -1021,8 +1023,8 @@
             auto [new_expr, new_ty, mat_name] =
                 BuildAccessExpr(expr, ty, chain, std140_mat_idx, dynamic_index);
             expr = new_expr;
-            auto* mat = ty->As<sem::Matrix>();
-            auto std140_mat = std140_mats.Get(ty->As<sem::Matrix>());
+            auto* mat = ty->As<type::Matrix>();
+            auto std140_mat = std140_mats.Get(ty->As<type::Matrix>());
             columns = utils::Transform(std140_mat->columns, [&](auto column_name) {
                 return b.MemberAccessor(b.Deref(let), column_name);
             });
@@ -1084,12 +1086,12 @@
                     auto* expr = b.IndexAccessor(lhs, idx);
                     return {expr, arr->ElemType(), name};
                 },  //
-                [&](const sem::Matrix* mat) -> ExprTypeName {
+                [&](const type::Matrix* mat) -> ExprTypeName {
                     auto* idx = dynamic_index(dyn_idx->slot);
                     auto* expr = b.IndexAccessor(lhs, idx);
                     return {expr, mat->ColumnType(), name};
                 },  //
-                [&](const sem::Vector* vec) -> ExprTypeName {
+                [&](const type::Vector* vec) -> ExprTypeName {
                     auto* idx = dynamic_index(dyn_idx->slot);
                     auto* expr = b.IndexAccessor(lhs, idx);
                     return {expr, vec->type(), name};
@@ -1104,13 +1106,13 @@
             /// The access is a vector swizzle.
             return Switch(
                 ty,  //
-                [&](const sem::Vector* vec) -> ExprTypeName {
+                [&](const type::Vector* vec) -> ExprTypeName {
                     static const char xyzw[] = {'x', 'y', 'z', 'w'};
                     std::string rhs;
                     for (auto el : *swizzle) {
                         rhs += xyzw[el];
                     }
-                    auto swizzle_ty = src->Types().Find<sem::Vector>(
+                    auto swizzle_ty = src->Types().Find<type::Vector>(
                         vec->type(), static_cast<uint32_t>(swizzle->Length()));
                     auto* expr = b.MemberAccessor(lhs, rhs);
                     return {expr, swizzle_ty, rhs};
@@ -1136,11 +1138,11 @@
                 auto* expr = b.IndexAccessor(lhs, idx);
                 return {expr, arr->ElemType(), std::to_string(idx)};
             },  //
-            [&](const sem::Matrix* mat) -> ExprTypeName {
+            [&](const type::Matrix* mat) -> ExprTypeName {
                 auto* expr = b.IndexAccessor(lhs, idx);
                 return {expr, mat->ColumnType(), std::to_string(idx)};
             },  //
-            [&](const sem::Vector* vec) -> ExprTypeName {
+            [&](const type::Vector* vec) -> ExprTypeName {
                 auto* expr = b.IndexAccessor(lhs, idx);
                 return {expr, vec->type(), std::to_string(idx)};
             },  //
diff --git a/src/tint/transform/transform.cc b/src/tint/transform/transform.cc
index 1be2758..d2bb8eb 100644
--- a/src/tint/transform/transform.cc
+++ b/src/tint/transform/transform.cc
@@ -92,11 +92,11 @@
     if (ty->Is<type::Bool>()) {
         return ctx.dst->create<ast::Bool>();
     }
-    if (auto* m = ty->As<sem::Matrix>()) {
+    if (auto* m = ty->As<type::Matrix>()) {
         auto* el = CreateASTTypeFor(ctx, m->type());
         return ctx.dst->create<ast::Matrix>(el, m->rows(), m->columns());
     }
-    if (auto* v = ty->As<sem::Vector>()) {
+    if (auto* v = ty->As<type::Vector>()) {
         auto* el = CreateASTTypeFor(ctx, v->type());
         return ctx.dst->create<ast::Vector>(el, v->Width());
     }
diff --git a/src/tint/transform/transform_test.cc b/src/tint/transform/transform_test.cc
index 70e0c3a..8f20c14 100644
--- a/src/tint/transform/transform_test.cc
+++ b/src/tint/transform/transform_test.cc
@@ -50,8 +50,8 @@
 
 TEST_F(CreateASTTypeForTest, Matrix) {
     auto* mat = create([](ProgramBuilder& b) {
-        auto* column_type = b.create<sem::Vector>(b.create<type::F32>(), 2u);
-        return b.create<sem::Matrix>(column_type, 3u);
+        auto* column_type = b.create<type::Vector>(b.create<type::F32>(), 2u);
+        return b.create<type::Matrix>(column_type, 3u);
     });
     ASSERT_TRUE(mat->Is<ast::Matrix>());
     ASSERT_TRUE(mat->As<ast::Matrix>()->type->Is<ast::F32>());
@@ -61,7 +61,7 @@
 
 TEST_F(CreateASTTypeForTest, Vector) {
     auto* vec =
-        create([](ProgramBuilder& b) { return b.create<sem::Vector>(b.create<type::F32>(), 2u); });
+        create([](ProgramBuilder& b) { return b.create<type::Vector>(b.create<type::F32>(), 2u); });
     ASSERT_TRUE(vec->Is<ast::Vector>());
     ASSERT_TRUE(vec->As<ast::Vector>()->type->Is<ast::F32>());
     ASSERT_EQ(vec->As<ast::Vector>()->width, 2u);
diff --git a/src/tint/transform/var_for_dynamic_index.cc b/src/tint/transform/var_for_dynamic_index.cc
index c2fb0a5..1039ca2 100644
--- a/src/tint/transform/var_for_dynamic_index.cc
+++ b/src/tint/transform/var_for_dynamic_index.cc
@@ -47,7 +47,7 @@
         }
 
         auto* indexed = sem.Get(object_expr);
-        if (!indexed->Type()->IsAnyOf<sem::Array, sem::Matrix>()) {
+        if (!indexed->Type()->IsAnyOf<sem::Array, type::Matrix>()) {
             // We only care about array and matrices.
             return true;
         }
diff --git a/src/tint/transform/vectorize_matrix_conversions.cc b/src/tint/transform/vectorize_matrix_conversions.cc
index cbb1624..714e61e 100644
--- a/src/tint/transform/vectorize_matrix_conversions.cc
+++ b/src/tint/transform/vectorize_matrix_conversions.cc
@@ -36,7 +36,7 @@
     for (auto* node : program->ASTNodes().Objects()) {
         if (auto* sem = program->Sem().Get<sem::Expression>(node)) {
             if (auto* call = sem->UnwrapMaterialize()->As<sem::Call>()) {
-                if (call->Target()->Is<sem::TypeConversion>() && call->Type()->Is<sem::Matrix>()) {
+                if (call->Target()->Is<sem::TypeConversion>() && call->Type()->Is<type::Matrix>()) {
                     auto& args = call->Arguments();
                     if (args.Length() == 1 && args[0]->Type()->UnwrapRef()->is_float_matrix()) {
                         return true;
@@ -65,7 +65,7 @@
     CloneContext ctx{&b, src, /* auto_clone_symbols */ true};
 
     using HelperFunctionKey =
-        utils::UnorderedKeyWrapper<std::tuple<const sem::Matrix*, const sem::Matrix*>>;
+        utils::UnorderedKeyWrapper<std::tuple<const type::Matrix*, const type::Matrix*>>;
 
     std::unordered_map<HelperFunctionKey, Symbol> matrix_convs;
 
@@ -75,7 +75,7 @@
         if (!ty_conv) {
             return nullptr;
         }
-        auto* dst_type = call->Type()->As<sem::Matrix>();
+        auto* dst_type = call->Type()->As<type::Matrix>();
         if (!dst_type) {
             return nullptr;
         }
@@ -87,7 +87,7 @@
 
         auto& matrix = args[0];
 
-        auto* src_type = matrix->Type()->UnwrapRef()->As<sem::Matrix>();
+        auto* src_type = matrix->Type()->UnwrapRef()->As<type::Matrix>();
         if (!src_type) {
             return nullptr;
         }
diff --git a/src/tint/transform/vectorize_scalar_matrix_initializers.cc b/src/tint/transform/vectorize_scalar_matrix_initializers.cc
index 27ccf40..2a3a37c 100644
--- a/src/tint/transform/vectorize_scalar_matrix_initializers.cc
+++ b/src/tint/transform/vectorize_scalar_matrix_initializers.cc
@@ -32,7 +32,7 @@
 bool ShouldRun(const Program* program) {
     for (auto* node : program->ASTNodes().Objects()) {
         if (auto* call = program->Sem().Get<sem::Call>(node)) {
-            if (call->Target()->Is<sem::TypeInitializer>() && call->Type()->Is<sem::Matrix>()) {
+            if (call->Target()->Is<sem::TypeInitializer>() && call->Type()->Is<type::Matrix>()) {
                 auto& args = call->Arguments();
                 if (!args.IsEmpty() && args[0]->Type()->UnwrapRef()->is_scalar()) {
                     return true;
@@ -59,7 +59,7 @@
     ProgramBuilder b;
     CloneContext ctx{&b, src, /* auto_clone_symbols */ true};
 
-    std::unordered_map<const sem::Matrix*, Symbol> scalar_inits;
+    std::unordered_map<const type::Matrix*, Symbol> scalar_inits;
 
     ctx.ReplaceAll([&](const ast::CallExpression* expr) -> const ast::CallExpression* {
         auto* call = src->Sem().Get(expr)->UnwrapMaterialize()->As<sem::Call>();
@@ -67,7 +67,7 @@
         if (!ty_init) {
             return nullptr;
         }
-        auto* mat_type = call->Type()->As<sem::Matrix>();
+        auto* mat_type = call->Type()->As<type::Matrix>();
         if (!mat_type) {
             return nullptr;
         }
@@ -84,7 +84,7 @@
         if (args[0]
                 ->Type()
                 ->UnwrapRef()
-                ->IsAnyOf<sem::Matrix, sem::Vector, type::AbstractNumeric>()) {
+                ->IsAnyOf<type::Matrix, type::Vector, type::AbstractNumeric>()) {
             return nullptr;
         }
 
diff --git a/src/tint/transform/vertex_pulling.cc b/src/tint/transform/vertex_pulling.cc
index d014c61..a5cb94a 100644
--- a/src/tint/transform/vertex_pulling.cc
+++ b/src/tint/transform/vertex_pulling.cc
@@ -165,7 +165,7 @@
         [](const type::F16*) -> AttributeWGSLType {
             return {BaseWGSLType::kF16, 1};
         },
-        [](const sem::Vector* vec) -> AttributeWGSLType {
+        [](const type::Vector* vec) -> AttributeWGSLType {
             return {WGSLTypeOf(vec->type()).base_type, vec->Width()};
         },
         [](Default) -> AttributeWGSLType {
diff --git a/src/tint/sem/matrix.cc b/src/tint/type/matrix.cc
similarity index 90%
rename from src/tint/sem/matrix.cc
rename to src/tint/type/matrix.cc
index 1809016..ecc2250 100644
--- a/src/tint/sem/matrix.cc
+++ b/src/tint/type/matrix.cc
@@ -1,4 +1,4 @@
-// Copyright 2020 The Tint Authors.
+// Copyright 2022 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.
@@ -12,15 +12,15 @@
 // See the License for the specific language governing permissions and
 // limitations under the License.
 
-#include "src/tint/sem/matrix.h"
+#include "src/tint/type/matrix.h"
 
 #include "src/tint/program_builder.h"
-#include "src/tint/sem/vector.h"
+#include "src/tint/type/vector.h"
 #include "src/tint/utils/hash.h"
 
-TINT_INSTANTIATE_TYPEINFO(tint::sem::Matrix);
+TINT_INSTANTIATE_TYPEINFO(tint::type::Matrix);
 
-namespace tint::sem {
+namespace tint::type {
 
 Matrix::Matrix(const Vector* column_type, uint32_t columns)
     : Base(type::TypeFlags{
@@ -71,4 +71,4 @@
     return column_type_->Align();
 }
 
-}  // namespace tint::sem
+}  // namespace tint::type
diff --git a/src/tint/sem/matrix.h b/src/tint/type/matrix.h
similarity index 90%
rename from src/tint/sem/matrix.h
rename to src/tint/type/matrix.h
index 8349410..52025c6 100644
--- a/src/tint/sem/matrix.h
+++ b/src/tint/type/matrix.h
@@ -1,4 +1,4 @@
-// Copyright 2020 The Tint Authors.
+// Copyright 2022 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.
@@ -12,19 +12,19 @@
 // See the License for the specific language governing permissions and
 // limitations under the License.
 
-#ifndef SRC_TINT_SEM_MATRIX_H_
-#define SRC_TINT_SEM_MATRIX_H_
+#ifndef SRC_TINT_TYPE_MATRIX_H_
+#define SRC_TINT_TYPE_MATRIX_H_
 
 #include <string>
 
 #include "src/tint/type/type.h"
 
 // Forward declarations
-namespace tint::sem {
+namespace tint::type {
 class Vector;
-}  // namespace tint::sem
+}  // namespace tint::type
 
-namespace tint::sem {
+namespace tint::type {
 
 /// A matrix type
 class Matrix final : public Castable<Matrix, type::Type> {
@@ -76,6 +76,6 @@
     const uint32_t columns_;
 };
 
-}  // namespace tint::sem
+}  // namespace tint::type
 
-#endif  // SRC_TINT_SEM_MATRIX_H_
+#endif  // SRC_TINT_TYPE_MATRIX_H_
diff --git a/src/tint/sem/matrix_test.cc b/src/tint/type/matrix_test.cc
similarity index 95%
rename from src/tint/sem/matrix_test.cc
rename to src/tint/type/matrix_test.cc
index 5ff13dc..7cd06c3 100644
--- a/src/tint/sem/matrix_test.cc
+++ b/src/tint/type/matrix_test.cc
@@ -1,4 +1,4 @@
-// Copyright 2020 The Tint Authors.
+// Copyright 2022 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.
@@ -12,10 +12,10 @@
 // See the License for the specific language governing permissions and
 // limitations under the License.
 
-#include "src/tint/sem/test_helper.h"
+#include "src/tint/type/test_helper.h"
 #include "src/tint/type/texture.h"
 
-namespace tint::sem {
+namespace tint::type {
 namespace {
 
 using MatrixTest = TestHelper;
@@ -72,4 +72,4 @@
 }
 
 }  // namespace
-}  // namespace tint::sem
+}  // namespace tint::type
diff --git a/src/tint/type/type.cc b/src/tint/type/type.cc
index 43026e1..3250033 100644
--- a/src/tint/type/type.cc
+++ b/src/tint/type/type.cc
@@ -15,20 +15,20 @@
 #include "src/tint/type/type.h"
 
 #include "src/tint/sem/array.h"
-#include "src/tint/sem/matrix.h"
 #include "src/tint/sem/struct.h"
-#include "src/tint/sem/vector.h"
 #include "src/tint/type/abstract_float.h"
 #include "src/tint/type/abstract_int.h"
 #include "src/tint/type/bool.h"
 #include "src/tint/type/f16.h"
 #include "src/tint/type/f32.h"
 #include "src/tint/type/i32.h"
+#include "src/tint/type/matrix.h"
 #include "src/tint/type/pointer.h"
 #include "src/tint/type/reference.h"
 #include "src/tint/type/sampler.h"
 #include "src/tint/type/texture.h"
 #include "src/tint/type/u32.h"
+#include "src/tint/type/vector.h"
 
 TINT_INSTANTIATE_TYPEINFO(tint::type::Type);
 
@@ -81,17 +81,17 @@
 }
 
 bool Type::is_float_matrix() const {
-    return Is([](const sem::Matrix* m) { return m->type()->is_float_scalar(); });
+    return Is([](const type::Matrix* m) { return m->type()->is_float_scalar(); });
 }
 
 bool Type::is_square_float_matrix() const {
-    return Is([](const sem::Matrix* m) {
+    return Is([](const type::Matrix* m) {
         return m->type()->is_float_scalar() && m->rows() == m->columns();
     });
 }
 
 bool Type::is_float_vector() const {
-    return Is([](const sem::Vector* v) { return v->type()->is_float_scalar(); });
+    return Is([](const type::Vector* v) { return v->type()->is_float_scalar(); });
 }
 
 bool Type::is_float_scalar_or_vector() const {
@@ -116,11 +116,11 @@
 
 bool Type::is_signed_integer_vector() const {
     return Is(
-        [](const sem::Vector* v) { return v->type()->IsAnyOf<type::I32, type::AbstractInt>(); });
+        [](const type::Vector* v) { return v->type()->IsAnyOf<type::I32, type::AbstractInt>(); });
 }
 
 bool Type::is_unsigned_integer_vector() const {
-    return Is([](const sem::Vector* v) { return v->type()->Is<type::U32>(); });
+    return Is([](const type::Vector* v) { return v->type()->Is<type::U32>(); });
 }
 
 bool Type::is_unsigned_integer_scalar_or_vector() const {
@@ -136,11 +136,11 @@
 }
 
 bool Type::is_abstract_integer_vector() const {
-    return Is([](const sem::Vector* v) { return v->type()->Is<type::AbstractInt>(); });
+    return Is([](const type::Vector* v) { return v->type()->Is<type::AbstractInt>(); });
 }
 
 bool Type::is_abstract_float_vector() const {
-    return Is([](const sem::Vector* v) { return v->type()->Is<type::AbstractFloat>(); });
+    return Is([](const type::Vector* v) { return v->type()->Is<type::AbstractFloat>(); });
 }
 
 bool Type::is_abstract_integer_scalar_or_vector() const {
@@ -152,7 +152,7 @@
 }
 
 bool Type::is_bool_vector() const {
-    return Is([](const sem::Vector* v) { return v->type()->Is<type::Bool>(); });
+    return Is([](const type::Vector* v) { return v->type()->Is<type::Bool>(); });
 }
 
 bool Type::is_bool_scalar_or_vector() const {
@@ -160,11 +160,11 @@
 }
 
 bool Type::is_numeric_vector() const {
-    return Is([](const sem::Vector* v) { return v->type()->is_numeric_scalar(); });
+    return Is([](const type::Vector* v) { return v->type()->is_numeric_scalar(); });
 }
 
 bool Type::is_scalar_vector() const {
-    return Is([](const sem::Vector* v) { return v->type()->is_scalar(); });
+    return Is([](const type::Vector* v) { return v->type()->is_scalar(); });
 }
 
 bool Type::is_numeric_scalar_or_vector() const {
@@ -179,8 +179,8 @@
     return Switch(
         this,  //
         [&](const type::AbstractNumeric*) { return true; },
-        [&](const sem::Vector* v) { return v->type()->HoldsAbstract(); },
-        [&](const sem::Matrix* m) { return m->type()->HoldsAbstract(); },
+        [&](const type::Vector* v) { return v->type()->HoldsAbstract(); },
+        [&](const type::Matrix* m) { return m->type()->HoldsAbstract(); },
         [&](const sem::Array* a) { return a->ElemType()->HoldsAbstract(); },
         [&](const sem::Struct* s) {
             for (auto* m : s->Members()) {
@@ -215,16 +215,16 @@
                 [&](const type::F16*) { return 7; },            //
                 [&](Default) { return kNoConversion; });
         },
-        [&](const sem::Vector* from_vec) {
-            if (auto* to_vec = to->As<sem::Vector>()) {
+        [&](const type::Vector* from_vec) {
+            if (auto* to_vec = to->As<type::Vector>()) {
                 if (from_vec->Width() == to_vec->Width()) {
                     return ConversionRank(from_vec->type(), to_vec->type());
                 }
             }
             return kNoConversion;
         },
-        [&](const sem::Matrix* from_mat) {
-            if (auto* to_mat = to->As<sem::Matrix>()) {
+        [&](const type::Matrix* from_mat) {
+            if (auto* to_mat = to->As<type::Matrix>()) {
                 if (from_mat->columns() == to_mat->columns() &&
                     from_mat->rows() == to_mat->rows()) {
                     return ConversionRank(from_mat->type(), to_mat->type());
@@ -261,13 +261,13 @@
     }
     return Switch(
         ty,  //
-        [&](const sem::Vector* v) {
+        [&](const type::Vector* v) {
             if (count) {
                 *count = v->Width();
             }
             return v->type();
         },
-        [&](const sem::Matrix* m) {
+        [&](const type::Matrix* m) {
             if (count) {
                 *count = m->columns();
             }
diff --git a/src/tint/type/type_test.cc b/src/tint/type/type_test.cc
index 60fb6c7..cbb2e2a 100644
--- a/src/tint/type/type_test.cc
+++ b/src/tint/type/type_test.cc
@@ -29,20 +29,20 @@
     const type::F16* f16 = create<type::F16>();
     const type::I32* i32 = create<type::I32>();
     const type::U32* u32 = create<type::U32>();
-    const sem::Vector* vec2_f32 = create<sem::Vector>(f32, 2u);
-    const sem::Vector* vec3_f32 = create<sem::Vector>(f32, 3u);
-    const sem::Vector* vec3_f16 = create<sem::Vector>(f16, 3u);
-    const sem::Vector* vec4_f32 = create<sem::Vector>(f32, 4u);
-    const sem::Vector* vec3_u32 = create<sem::Vector>(u32, 3u);
-    const sem::Vector* vec3_i32 = create<sem::Vector>(i32, 3u);
-    const sem::Vector* vec3_af = create<sem::Vector>(af, 3u);
-    const sem::Vector* vec3_ai = create<sem::Vector>(ai, 3u);
-    const sem::Matrix* mat2x4_f32 = create<sem::Matrix>(vec4_f32, 2u);
-    const sem::Matrix* mat3x4_f32 = create<sem::Matrix>(vec4_f32, 3u);
-    const sem::Matrix* mat4x2_f32 = create<sem::Matrix>(vec2_f32, 4u);
-    const sem::Matrix* mat4x3_f32 = create<sem::Matrix>(vec3_f32, 4u);
-    const sem::Matrix* mat4x3_f16 = create<sem::Matrix>(vec3_f16, 4u);
-    const sem::Matrix* mat4x3_af = create<sem::Matrix>(vec3_af, 4u);
+    const type::Vector* vec2_f32 = create<type::Vector>(f32, 2u);
+    const type::Vector* vec3_f32 = create<type::Vector>(f32, 3u);
+    const type::Vector* vec3_f16 = create<type::Vector>(f16, 3u);
+    const type::Vector* vec4_f32 = create<type::Vector>(f32, 4u);
+    const type::Vector* vec3_u32 = create<type::Vector>(u32, 3u);
+    const type::Vector* vec3_i32 = create<type::Vector>(i32, 3u);
+    const type::Vector* vec3_af = create<type::Vector>(af, 3u);
+    const type::Vector* vec3_ai = create<type::Vector>(ai, 3u);
+    const type::Matrix* mat2x4_f32 = create<type::Matrix>(vec4_f32, 2u);
+    const type::Matrix* mat3x4_f32 = create<type::Matrix>(vec4_f32, 3u);
+    const type::Matrix* mat4x2_f32 = create<type::Matrix>(vec2_f32, 4u);
+    const type::Matrix* mat4x3_f32 = create<type::Matrix>(vec3_f32, 4u);
+    const type::Matrix* mat4x3_f16 = create<type::Matrix>(vec3_f16, 4u);
+    const type::Matrix* mat4x3_af = create<type::Matrix>(vec3_af, 4u);
     const type::Reference* ref_u32 =
         create<type::Reference>(u32, ast::AddressSpace::kPrivate, ast::Access::kReadWrite);
     const sem::Struct* str_f32 = create<sem::Struct>(nullptr,
diff --git a/src/tint/sem/vector.cc b/src/tint/type/vector.cc
similarity index 87%
rename from src/tint/sem/vector.cc
rename to src/tint/type/vector.cc
index 650b58e..a044613 100644
--- a/src/tint/sem/vector.cc
+++ b/src/tint/type/vector.cc
@@ -1,4 +1,4 @@
-// Copyright 2020 The Tint Authors.
+// Copyright 2022 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.
@@ -12,14 +12,14 @@
 // See the License for the specific language governing permissions and
 // limitations under the License.
 
-#include "src/tint/sem/vector.h"
+#include "src/tint/type/vector.h"
 
 #include "src/tint/program_builder.h"
 #include "src/tint/utils/hash.h"
 
-TINT_INSTANTIATE_TYPEINFO(tint::sem::Vector);
+TINT_INSTANTIATE_TYPEINFO(tint::type::Vector);
 
-namespace tint::sem {
+namespace tint::type {
 
 Vector::Vector(Type const* subtype, uint32_t width)
     : Base(type::TypeFlags{
@@ -29,8 +29,8 @@
       }),
       subtype_(subtype),
       width_(width) {
-    TINT_ASSERT(Semantic, width_ > 1);
-    TINT_ASSERT(Semantic, width_ < 5);
+    TINT_ASSERT(Type, width_ > 1);
+    TINT_ASSERT(Type, width_ < 5);
 }
 
 Vector::Vector(Vector&&) = default;
@@ -70,4 +70,4 @@
     return 0;  // Unreachable
 }
 
-}  // namespace tint::sem
+}  // namespace tint::type
diff --git a/src/tint/sem/vector.h b/src/tint/type/vector.h
similarity index 92%
rename from src/tint/sem/vector.h
rename to src/tint/type/vector.h
index cfe92cb..ba84c82 100644
--- a/src/tint/sem/vector.h
+++ b/src/tint/type/vector.h
@@ -1,4 +1,4 @@
-// Copyright 2020 The Tint Authors.
+// Copyright 2022 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.
@@ -12,14 +12,14 @@
 // See the License for the specific language governing permissions and
 // limitations under the License.
 
-#ifndef SRC_TINT_SEM_VECTOR_H_
-#define SRC_TINT_SEM_VECTOR_H_
+#ifndef SRC_TINT_TYPE_VECTOR_H_
+#define SRC_TINT_TYPE_VECTOR_H_
 
 #include <string>
 
 #include "src/tint/type/type.h"
 
-namespace tint::sem {
+namespace tint::type {
 
 /// A vector type.
 class Vector final : public Castable<Vector, type::Type> {
@@ -70,6 +70,6 @@
     const uint32_t width_;
 };
 
-}  // namespace tint::sem
+}  // namespace tint::type
 
-#endif  // SRC_TINT_SEM_VECTOR_H_
+#endif  // SRC_TINT_TYPE_VECTOR_H_
diff --git a/src/tint/sem/vector_test.cc b/src/tint/type/vector_test.cc
similarity index 93%
rename from src/tint/sem/vector_test.cc
rename to src/tint/type/vector_test.cc
index a20f0d7..b83ab51 100644
--- a/src/tint/sem/vector_test.cc
+++ b/src/tint/type/vector_test.cc
@@ -1,4 +1,4 @@
-// Copyright 2020 The Tint Authors.
+// Copyright 2022 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.
@@ -12,10 +12,10 @@
 // See the License for the specific language governing permissions and
 // limitations under the License.
 
-#include "src/tint/sem/test_helper.h"
+#include "src/tint/type/test_helper.h"
 #include "src/tint/type/texture.h"
 
-namespace tint::sem {
+namespace tint::type {
 namespace {
 
 using VectorTest = TestHelper;
@@ -64,4 +64,4 @@
 }
 
 }  // namespace
-}  // namespace tint::sem
+}  // namespace tint::type
diff --git a/src/tint/writer/append_vector.cc b/src/tint/writer/append_vector.cc
index 97bae38..4503041 100644
--- a/src/tint/writer/append_vector.cc
+++ b/src/tint/writer/append_vector.cc
@@ -36,7 +36,7 @@
 VectorInitializerInfo AsVectorInitializer(const sem::Expression* expr) {
     if (auto* call = expr->As<sem::Call>()) {
         if (auto* ctor = call->Target()->As<sem::TypeInitializer>()) {
-            if (ctor->ReturnType()->Is<sem::Vector>()) {
+            if (ctor->ReturnType()->Is<type::Vector>()) {
                 return {call, ctor};
             }
         }
@@ -76,7 +76,7 @@
     auto* vector_sem = b->Sem().Get(vector_ast);
     auto* scalar_sem = b->Sem().Get(scalar_ast);
     auto* vector_ty = vector_sem->Type()->UnwrapRef();
-    if (auto* vec = vector_ty->As<sem::Vector>()) {
+    if (auto* vec = vector_ty->As<type::Vector>()) {
         packed_size = vec->Width() + 1;
         packed_el_sem_ty = vec->type();
     } else {
@@ -101,7 +101,7 @@
     auto* statement = vector_sem->Stmt();
 
     auto* packed_ast_ty = b->create<ast::Vector>(packed_el_ast_ty, packed_size);
-    auto* packed_sem_ty = b->create<sem::Vector>(packed_el_sem_ty, packed_size);
+    auto* packed_sem_ty = b->create<type::Vector>(packed_el_sem_ty, packed_size);
 
     // If the coordinates are already passed in a vector initializer, with only
     // scalar components supplied, extract the elements into the new vector
diff --git a/src/tint/writer/append_vector_test.cc b/src/tint/writer/append_vector_test.cc
index 1164f54..e13ed3d 100644
--- a/src/tint/writer/append_vector_test.cc
+++ b/src/tint/writer/append_vector_test.cc
@@ -55,9 +55,9 @@
 
     auto* ctor = call->Target()->As<sem::TypeInitializer>();
     ASSERT_NE(ctor, nullptr);
-    ASSERT_TRUE(ctor->ReturnType()->Is<sem::Vector>());
-    EXPECT_EQ(ctor->ReturnType()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(ctor->ReturnType()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(ctor->ReturnType()->Is<type::Vector>());
+    EXPECT_EQ(ctor->ReturnType()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(ctor->ReturnType()->As<type::Vector>()->type()->Is<type::I32>());
     EXPECT_EQ(ctor->ReturnType(), call->Type());
 
     ASSERT_EQ(ctor->Parameters().Length(), 3u);
@@ -99,9 +99,9 @@
 
     auto* ctor = call->Target()->As<sem::TypeInitializer>();
     ASSERT_NE(ctor, nullptr);
-    ASSERT_TRUE(ctor->ReturnType()->Is<sem::Vector>());
-    EXPECT_EQ(ctor->ReturnType()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(ctor->ReturnType()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(ctor->ReturnType()->Is<type::Vector>());
+    EXPECT_EQ(ctor->ReturnType()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(ctor->ReturnType()->As<type::Vector>()->type()->Is<type::I32>());
     EXPECT_EQ(ctor->ReturnType(), call->Type());
 
     ASSERT_EQ(ctor->Parameters().Length(), 3u);
@@ -150,13 +150,13 @@
 
     auto* ctor = call->Target()->As<sem::TypeInitializer>();
     ASSERT_NE(ctor, nullptr);
-    ASSERT_TRUE(ctor->ReturnType()->Is<sem::Vector>());
-    EXPECT_EQ(ctor->ReturnType()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(ctor->ReturnType()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(ctor->ReturnType()->Is<type::Vector>());
+    EXPECT_EQ(ctor->ReturnType()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(ctor->ReturnType()->As<type::Vector>()->type()->Is<type::I32>());
     EXPECT_EQ(ctor->ReturnType(), call->Type());
 
     ASSERT_EQ(ctor->Parameters().Length(), 2u);
-    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<sem::Vector>());
+    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<type::Vector>());
     EXPECT_TRUE(ctor->Parameters()[1]->Type()->Is<type::I32>());
 }
 
@@ -193,9 +193,9 @@
 
     auto* ctor = call->Target()->As<sem::TypeInitializer>();
     ASSERT_NE(ctor, nullptr);
-    ASSERT_TRUE(ctor->ReturnType()->Is<sem::Vector>());
-    EXPECT_EQ(ctor->ReturnType()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(ctor->ReturnType()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(ctor->ReturnType()->Is<type::Vector>());
+    EXPECT_EQ(ctor->ReturnType()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(ctor->ReturnType()->As<type::Vector>()->type()->Is<type::I32>());
     EXPECT_EQ(ctor->ReturnType(), call->Type());
 
     ASSERT_EQ(ctor->Parameters().Length(), 3u);
@@ -236,9 +236,9 @@
 
     auto* ctor = call->Target()->As<sem::TypeInitializer>();
     ASSERT_NE(ctor, nullptr);
-    ASSERT_TRUE(ctor->ReturnType()->Is<sem::Vector>());
-    EXPECT_EQ(ctor->ReturnType()->As<sem::Vector>()->Width(), 4u);
-    EXPECT_TRUE(ctor->ReturnType()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(ctor->ReturnType()->Is<type::Vector>());
+    EXPECT_EQ(ctor->ReturnType()->As<type::Vector>()->Width(), 4u);
+    EXPECT_TRUE(ctor->ReturnType()->As<type::Vector>()->type()->Is<type::I32>());
     EXPECT_EQ(ctor->ReturnType(), call->Type());
 
     ASSERT_EQ(ctor->Parameters().Length(), 4u);
@@ -274,13 +274,13 @@
 
     auto* ctor = call->Target()->As<sem::TypeInitializer>();
     ASSERT_NE(ctor, nullptr);
-    ASSERT_TRUE(ctor->ReturnType()->Is<sem::Vector>());
-    EXPECT_EQ(ctor->ReturnType()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(ctor->ReturnType()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(ctor->ReturnType()->Is<type::Vector>());
+    EXPECT_EQ(ctor->ReturnType()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(ctor->ReturnType()->As<type::Vector>()->type()->Is<type::I32>());
     EXPECT_EQ(ctor->ReturnType(), call->Type());
 
     ASSERT_EQ(ctor->Parameters().Length(), 2u);
-    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<sem::Vector>());
+    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<type::Vector>());
     EXPECT_TRUE(ctor->Parameters()[1]->Type()->Is<type::I32>());
 }
 
@@ -314,9 +314,9 @@
 
     auto* ctor = call->Target()->As<sem::TypeInitializer>();
     ASSERT_NE(ctor, nullptr);
-    ASSERT_TRUE(ctor->ReturnType()->Is<sem::Vector>());
-    EXPECT_EQ(ctor->ReturnType()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(ctor->ReturnType()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(ctor->ReturnType()->Is<type::Vector>());
+    EXPECT_EQ(ctor->ReturnType()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(ctor->ReturnType()->As<type::Vector>()->type()->Is<type::I32>());
     EXPECT_EQ(ctor->ReturnType(), call->Type());
 
     ASSERT_EQ(ctor->Parameters().Length(), 3u);
@@ -352,13 +352,13 @@
 
     auto* ctor = call->Target()->As<sem::TypeInitializer>();
     ASSERT_NE(ctor, nullptr);
-    ASSERT_TRUE(ctor->ReturnType()->Is<sem::Vector>());
-    EXPECT_EQ(ctor->ReturnType()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(ctor->ReturnType()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(ctor->ReturnType()->Is<type::Vector>());
+    EXPECT_EQ(ctor->ReturnType()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(ctor->ReturnType()->As<type::Vector>()->type()->Is<type::I32>());
     EXPECT_EQ(ctor->ReturnType(), call->Type());
 
     ASSERT_EQ(ctor->Parameters().Length(), 2u);
-    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<sem::Vector>());
+    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<type::Vector>());
     EXPECT_TRUE(ctor->Parameters()[1]->Type()->Is<type::I32>());
 }
 
@@ -393,13 +393,13 @@
 
     auto* ctor = call->Target()->As<sem::TypeInitializer>();
     ASSERT_NE(ctor, nullptr);
-    ASSERT_TRUE(ctor->ReturnType()->Is<sem::Vector>());
-    EXPECT_EQ(ctor->ReturnType()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(ctor->ReturnType()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(ctor->ReturnType()->Is<type::Vector>());
+    EXPECT_EQ(ctor->ReturnType()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(ctor->ReturnType()->As<type::Vector>()->type()->Is<type::I32>());
     EXPECT_EQ(ctor->ReturnType(), call->Type());
 
     ASSERT_EQ(ctor->Parameters().Length(), 2u);
-    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<sem::Vector>());
+    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<type::Vector>());
     EXPECT_TRUE(ctor->Parameters()[1]->Type()->Is<type::I32>());
 }
 
@@ -430,13 +430,13 @@
 
     auto* ctor = call->Target()->As<sem::TypeInitializer>();
     ASSERT_NE(ctor, nullptr);
-    ASSERT_TRUE(ctor->ReturnType()->Is<sem::Vector>());
-    EXPECT_EQ(ctor->ReturnType()->As<sem::Vector>()->Width(), 3u);
-    EXPECT_TRUE(ctor->ReturnType()->As<sem::Vector>()->type()->Is<type::Bool>());
+    ASSERT_TRUE(ctor->ReturnType()->Is<type::Vector>());
+    EXPECT_EQ(ctor->ReturnType()->As<type::Vector>()->Width(), 3u);
+    EXPECT_TRUE(ctor->ReturnType()->As<type::Vector>()->type()->Is<type::Bool>());
     EXPECT_EQ(ctor->ReturnType(), call->Type());
 
     ASSERT_EQ(ctor->Parameters().Length(), 2u);
-    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<sem::Vector>());
+    EXPECT_TRUE(ctor->Parameters()[0]->Type()->Is<type::Vector>());
     EXPECT_TRUE(ctor->Parameters()[1]->Type()->Is<type::Bool>());
 }
 
@@ -471,9 +471,9 @@
 
     auto* ctor = call->Target()->As<sem::TypeInitializer>();
     ASSERT_NE(ctor, nullptr);
-    ASSERT_TRUE(ctor->ReturnType()->Is<sem::Vector>());
-    EXPECT_EQ(ctor->ReturnType()->As<sem::Vector>()->Width(), 4u);
-    EXPECT_TRUE(ctor->ReturnType()->As<sem::Vector>()->type()->Is<type::I32>());
+    ASSERT_TRUE(ctor->ReturnType()->Is<type::Vector>());
+    EXPECT_EQ(ctor->ReturnType()->As<type::Vector>()->Width(), 4u);
+    EXPECT_TRUE(ctor->ReturnType()->As<type::Vector>()->type()->Is<type::I32>());
     EXPECT_EQ(ctor->ReturnType(), call->Type());
 
     ASSERT_EQ(ctor->Parameters().Length(), 4u);
diff --git a/src/tint/writer/glsl/generator_impl.cc b/src/tint/writer/glsl/generator_impl.cc
index 80f5f77..f4f4bef 100644
--- a/src/tint/writer/glsl/generator_impl.cc
+++ b/src/tint/writer/glsl/generator_impl.cc
@@ -1156,7 +1156,7 @@
 bool GeneratorImpl::EmitDotCall(std::ostream& out,
                                 const ast::CallExpression* expr,
                                 const sem::Builtin* builtin) {
-    auto* vec_ty = builtin->Parameters()[0]->Type()->As<sem::Vector>();
+    auto* vec_ty = builtin->Parameters()[0]->Type()->As<type::Vector>();
     std::string fn = "dot";
     if (vec_ty->type()->is_integer_scalar()) {
         // GLSL does not have a builtin for dot() with integer vector types.
@@ -1309,7 +1309,7 @@
     return CallBuiltinHelper(
         out, expr, builtin, [&](TextBuffer* b, const std::vector<std::string>& params) {
             const auto v = params[0];
-            if (auto* vec = builtin->ReturnType()->As<sem::Vector>()) {
+            if (auto* vec = builtin->ReturnType()->As<type::Vector>()) {
                 switch (vec->Width()) {
                     case 2: {
                         line(b) << "return unpackHalf2x16(packHalf2x16(" << v << "));";
@@ -1665,7 +1665,7 @@
     // GLSL builtin, we need to swizzle the expression to generate the correct
     // number of components.
     uint32_t wgsl_ret_width = 1;
-    if (auto* vec = builtin->ReturnType()->As<sem::Vector>()) {
+    if (auto* vec = builtin->ReturnType()->As<type::Vector>()) {
         wgsl_ret_width = vec->Width();
     }
     if (wgsl_ret_width < glsl_ret_width) {
@@ -2317,7 +2317,7 @@
             out << constant->As<AInt>() << "u";
             return true;
         },
-        [&](const sem::Vector* v) {
+        [&](const type::Vector* v) {
             if (!EmitType(out, v, ast::AddressSpace::kNone, ast::Access::kUndefined, "")) {
                 return false;
             }
@@ -2338,7 +2338,7 @@
             }
             return true;
         },
-        [&](const sem::Matrix* m) {
+        [&](const type::Matrix* m) {
             if (!EmitType(out, m, ast::AddressSpace::kNone, ast::Access::kUndefined, "")) {
                 return false;
             }
@@ -2446,7 +2446,7 @@
         out << "0";
     } else if (type->Is<type::U32>()) {
         out << "0u";
-    } else if (auto* vec = type->As<sem::Vector>()) {
+    } else if (auto* vec = type->As<type::Vector>()) {
         if (!EmitType(out, type, ast::AddressSpace::kNone, ast::Access::kReadWrite, "")) {
             return false;
         }
@@ -2459,7 +2459,7 @@
                 return false;
             }
         }
-    } else if (auto* mat = type->As<sem::Matrix>()) {
+    } else if (auto* mat = type->As<type::Matrix>()) {
         if (!EmitType(out, type, ast::AddressSpace::kNone, ast::Access::kReadWrite, "")) {
             return false;
         }
@@ -2879,7 +2879,7 @@
         out << "float16_t";
     } else if (type->Is<type::I32>()) {
         out << "int";
-    } else if (auto* mat = type->As<sem::Matrix>()) {
+    } else if (auto* mat = type->As<type::Matrix>()) {
         TINT_ASSERT(Writer, (mat->type()->IsAnyOf<type::F32, type::F16>()));
         if (mat->type()->Is<type::F16>()) {
             out << "f16";
@@ -2958,7 +2958,7 @@
         }
     } else if (type->Is<type::U32>()) {
         out << "uint";
-    } else if (auto* vec = type->As<sem::Vector>()) {
+    } else if (auto* vec = type->As<type::Vector>()) {
         auto width = vec->Width();
         if (vec->type()->Is<type::F32>() && width >= 1 && width <= 4) {
             out << "vec" << width;
@@ -3209,8 +3209,8 @@
     auto* u32 = builder_.create<type::U32>();
     if (type->Is<type::Bool>()) {
         return u32;
-    } else if (auto* vec = type->As<sem::Vector>()) {
-        return builder_.create<sem::Vector>(u32, vec->Width());
+    } else if (auto* vec = type->As<type::Vector>()) {
+        return builder_.create<type::Vector>(u32, vec->Width());
     } else {
         return nullptr;
     }
diff --git a/src/tint/writer/glsl/generator_impl.h b/src/tint/writer/glsl/generator_impl.h
index 1491f8f..a0bf3a5 100644
--- a/src/tint/writer/glsl/generator_impl.h
+++ b/src/tint/writer/glsl/generator_impl.h
@@ -516,8 +516,8 @@
     TextBuffer helpers_;  // Helper functions emitted at the top of the output
     std::function<bool()> emit_continuing_;
     std::unordered_map<const sem::Builtin*, std::string> builtins_;
-    std::unordered_map<const sem::Vector*, std::string> dynamic_vector_write_;
-    std::unordered_map<const sem::Vector*, std::string> int_dot_funcs_;
+    std::unordered_map<const type::Vector*, std::string> dynamic_vector_write_;
+    std::unordered_map<const type::Vector*, std::string> int_dot_funcs_;
     std::unordered_map<BinaryOperandType, std::string> float_modulo_funcs_;
     std::unordered_set<const sem::Struct*> emitted_structs_;
     bool requires_oes_sample_variables_ = false;
diff --git a/src/tint/writer/glsl/generator_impl_type_test.cc b/src/tint/writer/glsl/generator_impl_type_test.cc
index 7adf274..9212dbf 100644
--- a/src/tint/writer/glsl/generator_impl_type_test.cc
+++ b/src/tint/writer/glsl/generator_impl_type_test.cc
@@ -131,8 +131,8 @@
 
 TEST_F(GlslGeneratorImplTest_Type, EmitType_Matrix_F32) {
     auto* f32 = create<type::F32>();
-    auto* vec3 = create<sem::Vector>(f32, 3u);
-    auto* mat2x3 = create<sem::Matrix>(vec3, 2u);
+    auto* vec3 = create<type::Vector>(f32, 3u);
+    auto* mat2x3 = create<type::Matrix>(vec3, 2u);
 
     GeneratorImpl& gen = Build();
 
@@ -146,8 +146,8 @@
     Enable(ast::Extension::kF16);
 
     auto* f16 = create<type::F16>();
-    auto* vec3 = create<sem::Vector>(f16, 3u);
-    auto* mat2x3 = create<sem::Matrix>(vec3, 2u);
+    auto* vec3 = create<type::Vector>(f16, 3u);
+    auto* mat2x3 = create<type::Matrix>(vec3, 2u);
 
     GeneratorImpl& gen = Build();
 
@@ -243,7 +243,7 @@
 
 TEST_F(GlslGeneratorImplTest_Type, EmitType_Vector_F32) {
     auto* f32 = create<type::F32>();
-    auto* vec3 = create<sem::Vector>(f32, 3u);
+    auto* vec3 = create<type::Vector>(f32, 3u);
 
     GeneratorImpl& gen = Build();
 
@@ -257,7 +257,7 @@
     Enable(ast::Extension::kF16);
 
     auto* f16 = create<type::F16>();
-    auto* vec3 = create<sem::Vector>(f16, 3u);
+    auto* vec3 = create<type::Vector>(f16, 3u);
 
     GeneratorImpl& gen = Build();
 
diff --git a/src/tint/writer/hlsl/generator_impl.cc b/src/tint/writer/hlsl/generator_impl.cc
index 2b46e57..a92b2f6 100644
--- a/src/tint/writer/hlsl/generator_impl.cc
+++ b/src/tint/writer/hlsl/generator_impl.cc
@@ -367,7 +367,7 @@
 }
 
 bool GeneratorImpl::EmitDynamicVectorAssignment(const ast::AssignmentStatement* stmt,
-                                                const sem::Vector* vec) {
+                                                const type::Vector* vec) {
     auto name = utils::GetOrCreate(dynamic_vector_write_, vec, [&]() -> std::string {
         std::string fn;
         {
@@ -441,7 +441,7 @@
 }
 
 bool GeneratorImpl::EmitDynamicMatrixVectorAssignment(const ast::AssignmentStatement* stmt,
-                                                      const sem::Matrix* mat) {
+                                                      const type::Matrix* mat) {
     auto name = utils::GetOrCreate(dynamic_matrix_vector_write_, mat, [&]() -> std::string {
         std::string fn;
         {
@@ -507,7 +507,7 @@
 }
 
 bool GeneratorImpl::EmitDynamicMatrixScalarAssignment(const ast::AssignmentStatement* stmt,
-                                                      const sem::Matrix* mat) {
+                                                      const type::Matrix* mat) {
     auto* lhs_col_access = stmt->lhs->As<ast::IndexAccessorExpression>();
     auto* lhs_row_access = lhs_col_access->object->As<ast::IndexAccessorExpression>();
 
@@ -540,7 +540,7 @@
             line(&helpers_) << "switch (col) {";
             {
                 ScopedIndent si2(&helpers_);
-                auto* vec = TypeOf(lhs_row_access->object)->UnwrapRef()->As<sem::Vector>();
+                auto* vec = TypeOf(lhs_row_access->object)->UnwrapRef()->As<type::Vector>();
                 for (uint32_t i = 0; i < mat->columns(); ++i) {
                     line(&helpers_) << "case " << i << ":";
                     {
@@ -623,7 +623,7 @@
 
 bool GeneratorImpl::EmitBitcast(std::ostream& out, const ast::BitcastExpression* expr) {
     auto* type = TypeOf(expr);
-    if (auto* vec = type->UnwrapRef()->As<sem::Vector>()) {
+    if (auto* vec = type->UnwrapRef()->As<type::Vector>()) {
         type = vec->type();
     }
 
@@ -650,7 +650,7 @@
         // BUG(crbug.com/tint/1333): work around assignment of scalar to matrices
         // with at least one dynamic index
         if (auto* lhs_sub_access = lhs_access->object->As<ast::IndexAccessorExpression>()) {
-            if (auto* mat = TypeOf(lhs_sub_access->object)->UnwrapRef()->As<sem::Matrix>()) {
+            if (auto* mat = TypeOf(lhs_sub_access->object)->UnwrapRef()->As<type::Matrix>()) {
                 auto* rhs_col_idx_sem = builder_.Sem().Get(lhs_access->index);
                 auto* rhs_row_idx_sem = builder_.Sem().Get(lhs_sub_access->index);
                 if (!rhs_col_idx_sem->ConstantValue() || !rhs_row_idx_sem->ConstantValue()) {
@@ -661,7 +661,7 @@
         // BUG(crbug.com/tint/1333): work around assignment of vector to matrices
         // with dynamic indices
         const auto* lhs_access_type = TypeOf(lhs_access->object)->UnwrapRef();
-        if (auto* mat = lhs_access_type->As<sem::Matrix>()) {
+        if (auto* mat = lhs_access_type->As<type::Matrix>()) {
             auto* lhs_index_sem = builder_.Sem().Get(lhs_access->index);
             if (!lhs_index_sem->ConstantValue()) {
                 return EmitDynamicMatrixVectorAssignment(stmt, mat);
@@ -669,7 +669,7 @@
         }
         // BUG(crbug.com/tint/534): work around assignment to vectors with dynamic
         // indices
-        if (auto* vec = lhs_access_type->As<sem::Vector>()) {
+        if (auto* vec = lhs_access_type->As<type::Vector>()) {
             auto* rhs_sem = builder_.Sem().Get(lhs_access->index);
             if (!rhs_sem->ConstantValue()) {
                 return EmitDynamicVectorAssignment(stmt, vec);
@@ -729,9 +729,9 @@
     // Multiplying by a matrix requires the use of `mul` in order to get the
     // type of multiply we desire.
     if (expr->op == ast::BinaryOp::kMultiply &&
-        ((lhs_type->Is<sem::Vector>() && rhs_type->Is<sem::Matrix>()) ||
-         (lhs_type->Is<sem::Matrix>() && rhs_type->Is<sem::Vector>()) ||
-         (lhs_type->Is<sem::Matrix>() && rhs_type->Is<sem::Matrix>()))) {
+        ((lhs_type->Is<type::Vector>() && rhs_type->Is<type::Matrix>()) ||
+         (lhs_type->Is<type::Matrix>() && rhs_type->Is<type::Vector>()) ||
+         (lhs_type->Is<type::Matrix>() && rhs_type->Is<type::Matrix>()))) {
         // Matrices are transposed, so swap LHS and RHS.
         out << "mul(";
         if (!EmitExpression(out, expr->rhs)) {
@@ -1045,7 +1045,7 @@
 
     // Single parameter matrix initializers must be identity initializer.
     // It could also be conversions between f16 and f32 matrix when f16 is properly supported.
-    if (type->Is<sem::Matrix>() && call->Arguments().Length() == 1) {
+    if (type->Is<type::Matrix>() && call->Arguments().Length() == 1) {
         if (!ctor->Parameters()[0]->Type()->UnwrapRef()->is_float_matrix()) {
             TINT_UNREACHABLE(Writer, diagnostics_)
                 << "found a single-parameter matrix initializer that is not identity initializer";
@@ -1087,7 +1087,7 @@
     }
 
     if (is_single_value_vector_init) {
-        out << ")." << std::string(type->As<sem::Vector>()->Width(), 'x');
+        out << ")." << std::string(type->As<type::Vector>()->Width(), 'x');
     }
 
     out << (brackets ? "}" : ")");
@@ -1977,7 +1977,7 @@
             auto in = params[0];
 
             std::string width;
-            if (auto* vec = ty->As<sem::Vector>()) {
+            if (auto* vec = ty->As<type::Vector>()) {
                 width = std::to_string(vec->Width());
             }
 
@@ -2010,7 +2010,7 @@
             auto in = params[0];
 
             std::string width;
-            if (auto* vec = ty->As<sem::Vector>()) {
+            if (auto* vec = ty->As<type::Vector>()) {
                 width = std::to_string(vec->Width());
             }
 
@@ -2069,7 +2069,7 @@
                                           const sem::Builtin* builtin) {
     // Emulate by casting to min16float and back again.
     std::string width;
-    if (auto* vec = builtin->ReturnType()->As<sem::Vector>()) {
+    if (auto* vec = builtin->ReturnType()->As<type::Vector>()) {
         width = std::to_string(vec->Width());
     }
     out << "float" << width << "(min16float" << width << "(";
@@ -2607,7 +2607,7 @@
         // HLSL builtin, we need to swizzle the expression to generate the correct
         // number of components.
         uint32_t wgsl_ret_width = 1;
-        if (auto* vec = builtin->ReturnType()->As<sem::Vector>()) {
+        if (auto* vec = builtin->ReturnType()->As<type::Vector>()) {
             wgsl_ret_width = vec->Width();
         }
         if (wgsl_ret_width < hlsl_ret_width) {
@@ -3290,7 +3290,7 @@
             out << constant->As<AInt>() << "u";
             return true;
         },
-        [&](const sem::Vector* v) {
+        [&](const type::Vector* v) {
             if (constant->AllEqual()) {
                 {
                     ScopedParen sp(out);
@@ -3321,7 +3321,7 @@
             }
             return true;
         },
-        [&](const sem::Matrix* m) {
+        [&](const type::Matrix* m) {
             if (!EmitType(out, m, ast::AddressSpace::kNone, ast::Access::kUndefined, "")) {
                 return false;
             }
@@ -3479,7 +3479,7 @@
             out << value << "u";
             return true;
         },
-        [&](const sem::Vector* vec) {
+        [&](const type::Vector* vec) {
             if (!EmitType(out, type, ast::AddressSpace::kNone, ast::Access::kReadWrite, "")) {
                 return false;
             }
@@ -3494,7 +3494,7 @@
             }
             return true;
         },
-        [&](const sem::Matrix* mat) {
+        [&](const type::Matrix* mat) {
             if (!EmitType(out, type, ast::AddressSpace::kNone, ast::Access::kReadWrite, "")) {
                 return false;
             }
@@ -3970,7 +3970,7 @@
             out << "int";
             return true;
         },
-        [&](const sem::Matrix* mat) {
+        [&](const type::Matrix* mat) {
             if (mat->type()->Is<type::F16>()) {
                 // Use matrix<type, N, M> for f16 matrix
                 out << "matrix<";
@@ -4084,7 +4084,7 @@
             out << "uint";
             return true;
         },
-        [&](const sem::Vector* vec) {
+        [&](const type::Vector* vec) {
             auto width = vec->Width();
             if (vec->type()->Is<type::F32>() && width >= 1 && width <= 4) {
                 out << "float" << width;
diff --git a/src/tint/writer/hlsl/generator_impl.h b/src/tint/writer/hlsl/generator_impl.h
index 1258b00..50e8114 100644
--- a/src/tint/writer/hlsl/generator_impl.h
+++ b/src/tint/writer/hlsl/generator_impl.h
@@ -461,7 +461,7 @@
     /// via an accessor expression
     /// @param vec the vector type being assigned to
     /// @returns true on success
-    bool EmitDynamicVectorAssignment(const ast::AssignmentStatement* stmt, const sem::Vector* vec);
+    bool EmitDynamicVectorAssignment(const ast::AssignmentStatement* stmt, const type::Vector* vec);
     /// Emits call to a helper matrix assignment function for the input assignment
     /// statement and matrix type. This is used to work around FXC issues where
     /// assignment of a vector to a matrix with a dynamic index causes compilation
@@ -471,7 +471,7 @@
     /// @param mat the matrix type being assigned to
     /// @returns true on success
     bool EmitDynamicMatrixVectorAssignment(const ast::AssignmentStatement* stmt,
-                                           const sem::Matrix* mat);
+                                           const type::Matrix* mat);
     /// Emits call to a helper matrix assignment function for the input assignment
     /// statement and matrix type. This is used to work around FXC issues where
     /// assignment of a scalar to a matrix with at least one dynamic index causes
@@ -481,7 +481,7 @@
     /// @param mat the matrix type being assigned to
     /// @returns true on success
     bool EmitDynamicMatrixScalarAssignment(const ast::AssignmentStatement* stmt,
-                                           const sem::Matrix* mat);
+                                           const type::Matrix* mat);
 
     /// Handles generating a builtin method name
     /// @param builtin the semantic info for the builtin
@@ -542,11 +542,11 @@
 
     TextBuffer helpers_;  // Helper functions emitted at the top of the output
     std::function<bool()> emit_continuing_;
-    std::unordered_map<const sem::Matrix*, std::string> matrix_scalar_inits_;
+    std::unordered_map<const type::Matrix*, std::string> matrix_scalar_inits_;
     std::unordered_map<const sem::Builtin*, std::string> builtins_;
-    std::unordered_map<const sem::Vector*, std::string> dynamic_vector_write_;
-    std::unordered_map<const sem::Matrix*, std::string> dynamic_matrix_vector_write_;
-    std::unordered_map<const sem::Matrix*, std::string> dynamic_matrix_scalar_write_;
+    std::unordered_map<const type::Vector*, std::string> dynamic_vector_write_;
+    std::unordered_map<const type::Matrix*, std::string> dynamic_matrix_vector_write_;
+    std::unordered_map<const type::Matrix*, std::string> dynamic_matrix_scalar_write_;
     std::unordered_map<const type::Type*, std::string> value_or_one_if_zero_;
     std::unordered_set<const sem::Struct*> emitted_structs_;
 };
diff --git a/src/tint/writer/hlsl/generator_impl_type_test.cc b/src/tint/writer/hlsl/generator_impl_type_test.cc
index ed85b48..0b3b75e 100644
--- a/src/tint/writer/hlsl/generator_impl_type_test.cc
+++ b/src/tint/writer/hlsl/generator_impl_type_test.cc
@@ -129,8 +129,8 @@
 
 TEST_F(HlslGeneratorImplTest_Type, EmitType_Matrix_F16) {
     auto* f16 = create<type::F16>();
-    auto* vec3 = create<sem::Vector>(f16, 3u);
-    auto* mat2x3 = create<sem::Matrix>(vec3, 2u);
+    auto* vec3 = create<type::Vector>(f16, 3u);
+    auto* mat2x3 = create<type::Matrix>(vec3, 2u);
 
     GeneratorImpl& gen = Build();
 
@@ -142,8 +142,8 @@
 
 TEST_F(HlslGeneratorImplTest_Type, EmitType_Matrix_F32) {
     auto* f32 = create<type::F32>();
-    auto* vec3 = create<sem::Vector>(f32, 3u);
-    auto* mat2x3 = create<sem::Matrix>(vec3, 2u);
+    auto* vec3 = create<type::Vector>(f32, 3u);
+    auto* mat2x3 = create<type::Matrix>(vec3, 2u);
 
     GeneratorImpl& gen = Build();
 
@@ -251,7 +251,7 @@
 
 TEST_F(HlslGeneratorImplTest_Type, EmitType_Vector) {
     auto* f32 = create<type::F32>();
-    auto* vec3 = create<sem::Vector>(f32, 3u);
+    auto* vec3 = create<type::Vector>(f32, 3u);
 
     GeneratorImpl& gen = Build();
 
diff --git a/src/tint/writer/msl/generator_impl.cc b/src/tint/writer/msl/generator_impl.cc
index a6659d2..10c91ac 100644
--- a/src/tint/writer/msl/generator_impl.cc
+++ b/src/tint/writer/msl/generator_impl.cc
@@ -36,7 +36,6 @@
 #include "src/tint/sem/call.h"
 #include "src/tint/sem/constant.h"
 #include "src/tint/sem/function.h"
-#include "src/tint/sem/matrix.h"
 #include "src/tint/sem/member_accessor_expression.h"
 #include "src/tint/sem/module.h"
 #include "src/tint/sem/struct.h"
@@ -44,7 +43,6 @@
 #include "src/tint/sem/type_conversion.h"
 #include "src/tint/sem/type_initializer.h"
 #include "src/tint/sem/variable.h"
-#include "src/tint/sem/vector.h"
 #include "src/tint/transform/array_length_from_uniform.h"
 #include "src/tint/transform/builtin_polyfill.h"
 #include "src/tint/transform/canonicalize_entry_point_io.h"
@@ -68,12 +66,14 @@
 #include "src/tint/type/f16.h"
 #include "src/tint/type/f32.h"
 #include "src/tint/type/i32.h"
+#include "src/tint/type/matrix.h"
 #include "src/tint/type/multisampled_texture.h"
 #include "src/tint/type/pointer.h"
 #include "src/tint/type/reference.h"
 #include "src/tint/type/sampled_texture.h"
 #include "src/tint/type/storage_texture.h"
 #include "src/tint/type/u32.h"
+#include "src/tint/type/vector.h"
 #include "src/tint/type/void.h"
 #include "src/tint/utils/defer.h"
 #include "src/tint/utils/map.h"
@@ -135,7 +135,7 @@
                   const type::Type* curr_type,
                   const type::Type* target_type)
         : s(stream) {
-        auto* target_vec_type = target_type->As<sem::Vector>();
+        auto* target_vec_type = target_type->As<type::Vector>();
 
         // If we need to promote from scalar to vector, bitcast the scalar to the
         // vector element type.
@@ -495,8 +495,8 @@
     auto signed_type_of = [&](const type::Type* ty) -> const type::Type* {
         if (ty->is_integer_scalar()) {
             return builder_.create<type::I32>();
-        } else if (auto* v = ty->As<sem::Vector>()) {
-            return builder_.create<sem::Vector>(builder_.create<type::I32>(), v->Width());
+        } else if (auto* v = ty->As<type::Vector>()) {
+            return builder_.create<type::Vector>(builder_.create<type::I32>(), v->Width());
         }
         return {};
     };
@@ -504,8 +504,8 @@
     auto unsigned_type_of = [&](const type::Type* ty) -> const type::Type* {
         if (ty->is_integer_scalar()) {
             return builder_.create<type::U32>();
-        } else if (auto* v = ty->As<sem::Vector>()) {
-            return builder_.create<sem::Vector>(builder_.create<type::U32>(), v->Width());
+        } else if (auto* v = ty->As<type::Vector>()) {
+            return builder_.create<type::Vector>(builder_.create<type::U32>(), v->Width());
         }
         return {};
     };
@@ -533,9 +533,9 @@
         rhs_type->is_signed_integer_scalar_or_vector()) {
         // If lhs or rhs is a vector, use that type (support implicit scalar to
         // vector promotion)
-        auto* target_type = lhs_type->Is<sem::Vector>()
+        auto* target_type = lhs_type->Is<type::Vector>()
                                 ? lhs_type
-                                : (rhs_type->Is<sem::Vector>() ? rhs_type : lhs_type);
+                                : (rhs_type->Is<type::Vector>() ? rhs_type : lhs_type);
 
         // WGSL defines behaviour for signed overflow, MSL does not. For these
         // cases, bitcast operands to unsigned, then cast result to signed.
@@ -705,7 +705,7 @@
         }
         case sem::BuiltinType::kQuantizeToF16: {
             std::string width = "";
-            if (auto* vec = builtin->ReturnType()->As<sem::Vector>()) {
+            if (auto* vec = builtin->ReturnType()->As<type::Vector>()) {
                 width = std::to_string(vec->Width());
             }
             out << "float" << width << "(half" << width << "(";
@@ -1292,7 +1292,7 @@
 bool GeneratorImpl::EmitDotCall(std::ostream& out,
                                 const ast::CallExpression* expr,
                                 const sem::Builtin* builtin) {
-    auto* vec_ty = builtin->Parameters()[0]->Type()->As<sem::Vector>();
+    auto* vec_ty = builtin->Parameters()[0]->Type()->As<type::Vector>();
     std::string fn = "dot";
     if (vec_ty->type()->is_integer_scalar()) {
         // MSL does not have a builtin for dot() with integer vector types.
@@ -1343,7 +1343,7 @@
             auto in = params[0];
 
             std::string width;
-            if (auto* vec = ty->As<sem::Vector>()) {
+            if (auto* vec = ty->As<type::Vector>()) {
                 width = std::to_string(vec->Width());
             }
 
@@ -1369,7 +1369,7 @@
             auto in = params[0];
 
             std::string width;
-            if (auto* vec = ty->As<sem::Vector>()) {
+            if (auto* vec = ty->As<type::Vector>()) {
                 width = std::to_string(vec->Width());
             }
 
@@ -1632,10 +1632,10 @@
             out << "0u";
             return true;
         },
-        [&](const sem::Vector* vec) {  //
+        [&](const type::Vector* vec) {  //
             return EmitZeroValue(out, vec->type());
         },
-        [&](const sem::Matrix* mat) {
+        [&](const type::Matrix* mat) {
             if (!EmitType(out, mat, "")) {
                 return false;
             }
@@ -1681,7 +1681,7 @@
             out << constant->As<AInt>() << "u";
             return true;
         },
-        [&](const sem::Vector* v) {
+        [&](const type::Vector* v) {
             if (!EmitType(out, v, "")) {
                 return false;
             }
@@ -1705,7 +1705,7 @@
             }
             return true;
         },
-        [&](const sem::Matrix* m) {
+        [&](const type::Matrix* m) {
             if (!EmitType(out, m, "")) {
                 return false;
             }
@@ -2573,7 +2573,7 @@
             out << "int";
             return true;
         },
-        [&](const sem::Matrix* mat) {
+        [&](const type::Matrix* mat) {
             if (!EmitType(out, mat->type(), "")) {
                 return false;
             }
@@ -2699,7 +2699,7 @@
             out << "uint";
             return true;
         },
-        [&](const sem::Vector* vec) {
+        [&](const type::Vector* vec) {
             if (!EmitType(out, vec->type(), "")) {
                 return false;
             }
@@ -3098,7 +3098,7 @@
             return SizeAndAlign{2, 2};
         },
 
-        [&](const sem::Vector* vec) {
+        [&](const type::Vector* vec) {
             auto num_els = vec->Width();
             auto* el_ty = vec->type();
             SizeAndAlign el_size_align = MslPackedTypeSizeAndAlign(el_ty);
@@ -3120,7 +3120,7 @@
             return SizeAndAlign{};
         },
 
-        [&](const sem::Matrix* mat) {
+        [&](const type::Matrix* mat) {
             // https://developer.apple.com/metal/Metal-Shading-Language-Specification.pdf
             // 2.3 Matrix Data Types
             auto cols = mat->columns();
diff --git a/src/tint/writer/msl/generator_impl_type_test.cc b/src/tint/writer/msl/generator_impl_type_test.cc
index 12d234c..3b63013 100644
--- a/src/tint/writer/msl/generator_impl_type_test.cc
+++ b/src/tint/writer/msl/generator_impl_type_test.cc
@@ -187,8 +187,8 @@
 
 TEST_F(MslGeneratorImplTest, EmitType_Matrix_F32) {
     auto* f32 = create<type::F32>();
-    auto* vec3 = create<sem::Vector>(f32, 3u);
-    auto* mat2x3 = create<sem::Matrix>(vec3, 2u);
+    auto* vec3 = create<type::Vector>(f32, 3u);
+    auto* mat2x3 = create<type::Matrix>(vec3, 2u);
 
     GeneratorImpl& gen = Build();
 
@@ -199,8 +199,8 @@
 
 TEST_F(MslGeneratorImplTest, EmitType_Matrix_F16) {
     auto* f16 = create<type::F16>();
-    auto* vec3 = create<sem::Vector>(f16, 3u);
-    auto* mat2x3 = create<sem::Matrix>(vec3, 2u);
+    auto* vec3 = create<type::Vector>(f16, 3u);
+    auto* mat2x3 = create<type::Matrix>(vec3, 2u);
 
     GeneratorImpl& gen = Build();
 
@@ -710,7 +710,7 @@
 
 TEST_F(MslGeneratorImplTest, EmitType_Vector) {
     auto* f32 = create<type::F32>();
-    auto* vec3 = create<sem::Vector>(f32, 3u);
+    auto* vec3 = create<type::Vector>(f32, 3u);
 
     GeneratorImpl& gen = Build();
 
diff --git a/src/tint/writer/spirv/builder.cc b/src/tint/writer/spirv/builder.cc
index 8cdee56..b018316 100644
--- a/src/tint/writer/spirv/builder.cc
+++ b/src/tint/writer/spirv/builder.cc
@@ -37,13 +37,13 @@
 #include "src/tint/sem/type_conversion.h"
 #include "src/tint/sem/type_initializer.h"
 #include "src/tint/sem/variable.h"
-#include "src/tint/sem/vector.h"
 #include "src/tint/transform/add_block_attribute.h"
 #include "src/tint/type/depth_multisampled_texture.h"
 #include "src/tint/type/depth_texture.h"
 #include "src/tint/type/multisampled_texture.h"
 #include "src/tint/type/reference.h"
 #include "src/tint/type/sampled_texture.h"
+#include "src/tint/type/vector.h"
 #include "src/tint/utils/defer.h"
 #include "src/tint/utils/map.h"
 #include "src/tint/writer/append_vector.h"
@@ -89,11 +89,11 @@
 /// one or more levels of an arrays inside of `type`.
 /// @param type the given type, which must not be null
 /// @returns the nested matrix type, or nullptr if none
-const sem::Matrix* GetNestedMatrixType(const type::Type* type) {
+const type::Matrix* GetNestedMatrixType(const type::Type* type) {
     while (auto* arr = type->As<sem::Array>()) {
         type = arr->ElemType();
     }
-    return type->As<sem::Matrix>();
+    return type->As<type::Matrix>();
 }
 
 uint32_t builtin_to_glsl_method(const sem::Builtin* builtin) {
@@ -240,7 +240,7 @@
 
 /// @return the vector element type if ty is a vector, otherwise return ty.
 const type::Type* ElementTypeOf(const type::Type* ty) {
-    if (auto* v = ty->As<sem::Vector>()) {
+    if (auto* v = ty->As<type::Vector>()) {
         return v->type();
     }
     return ty;
@@ -917,7 +917,7 @@
     }
 
     // If the source is a vector, we use OpVectorExtractDynamic.
-    if (info->source_type->Is<sem::Vector>()) {
+    if (info->source_type->Is<type::Vector>()) {
         if (!push_function_inst(
                 spv::Op::OpVectorExtractDynamic,
                 {Operand(result_type_id), extract, Operand(info->source_id), Operand(idx_id)})) {
@@ -1294,10 +1294,10 @@
 
     bool can_cast_or_copy = result_type->is_scalar();
 
-    if (auto* res_vec = result_type->As<sem::Vector>()) {
+    if (auto* res_vec = result_type->As<type::Vector>()) {
         if (res_vec->type()->is_scalar()) {
             auto* value_type = args[0]->Type()->UnwrapRef();
-            if (auto* val_vec = value_type->As<sem::Vector>()) {
+            if (auto* val_vec = value_type->As<type::Vector>()) {
                 if (val_vec->type()->is_scalar()) {
                     can_cast_or_copy = res_vec->Width() == val_vec->Width();
                 }
@@ -1305,9 +1305,9 @@
         }
     }
 
-    if (auto* res_mat = result_type->As<sem::Matrix>()) {
+    if (auto* res_mat = result_type->As<type::Matrix>()) {
         auto* value_type = args[0]->Type()->UnwrapRef();
-        if (auto* val_mat = value_type->As<sem::Matrix>()) {
+        if (auto* val_mat = value_type->As<type::Matrix>()) {
             // Generate passthrough for matrices of the same type
             can_cast_or_copy = res_mat == val_mat;
         }
@@ -1325,7 +1325,7 @@
     bool result_is_constant_composite = initializer_is_const;
     bool result_is_spec_composite = false;
 
-    if (auto* vec = result_type->As<sem::Vector>()) {
+    if (auto* vec = result_type->As<type::Vector>()) {
         result_type = vec->type();
     }
 
@@ -1347,7 +1347,7 @@
         // If the result and value types are the same we can just use the object.
         // If the result is not a vector then we should have validated that the
         // value type is a correctly sized vector so we can just use it directly.
-        if (result_type == value_type || result_type->Is<sem::Matrix>() ||
+        if (result_type == value_type || result_type->Is<type::Matrix>() ||
             result_type->Is<sem::Array>() || result_type->Is<sem::Struct>()) {
             ops.push_back(Operand(id));
             continue;
@@ -1370,7 +1370,7 @@
         //
         // For cases 1 and 2, if the type is different we also may need to insert
         // a type cast.
-        if (auto* vec = value_type->As<sem::Vector>()) {
+        if (auto* vec = value_type->As<type::Vector>()) {
             auto* vec_type = vec->type();
 
             auto value_type_id = GenerateTypeIfNeeded(vec_type);
@@ -1418,7 +1418,7 @@
     auto* const init_result_type = call->Type()->UnwrapRef();
     if (args.Length() == 1 && init_result_type->is_scalar_vector() &&
         args[0]->Type()->UnwrapRef()->is_scalar()) {
-        size_t vec_size = init_result_type->As<sem::Vector>()->Width();
+        size_t vec_size = init_result_type->As<type::Vector>()->Width();
         for (size_t i = 0; i < (vec_size - 1); ++i) {
             ops.push_back(ops[kOpsFirstValueIdx]);
         }
@@ -1462,7 +1462,7 @@
         if (t->is_scalar()) {
             return t;
         }
-        if (auto* v = t->As<sem::Vector>()) {
+        if (auto* v = t->As<type::Vector>()) {
             return v->type();
         }
         return nullptr;
@@ -1497,13 +1497,13 @@
                (from_type->is_float_vector() && to_type->is_unsigned_integer_vector())) {
         op = spv::Op::OpConvertFToU;
     } else if (from_type->IsAnyOf<type::Bool, type::F32, type::I32, type::U32, type::F16,
-                                  sem::Vector>() &&
+                                  type::Vector>() &&
                from_type == to_type) {
         // Identity initializer for scalar and vector types
         return val_id;
     } else if ((from_type->is_float_scalar() && to_type->is_float_scalar()) ||
                (from_type->is_float_vector() && to_type->is_float_vector() &&
-                from_type->As<sem::Vector>()->Width() == to_type->As<sem::Vector>()->Width())) {
+                from_type->As<type::Vector>()->Width() == to_type->As<type::Vector>()->Width())) {
         // Convert between f32 and f16 types.
         // OpFConvert requires the scalar component types to be different, and the case of from_type
         // and to_type being the same floating point scalar or vector type, i.e. identity
@@ -1552,7 +1552,7 @@
             error_ = "invalid destination type for bool conversion";
             return false;
         }
-        if (auto* to_vec = to_type->As<sem::Vector>()) {
+        if (auto* to_vec = to_type->As<type::Vector>()) {
             // Splat the scalars into vectors.
             zero_id = GenerateConstantVectorSplatIfNeeded(to_vec, zero_id);
             one_id = GenerateConstantVectorSplatIfNeeded(to_vec, one_id);
@@ -1568,12 +1568,12 @@
         }
 
         return result_id;
-    } else if (from_type->Is<sem::Matrix>() && to_type->Is<sem::Matrix>()) {
+    } else if (from_type->Is<type::Matrix>() && to_type->Is<type::Matrix>()) {
         // SPIRV does not support matrix conversion, the only valid case is matrix identity
         // initializer. Matrix conversion between f32 and f16 should be transformed into vector
         // conversions for each column vectors by VectorizeMatrixConversions.
-        auto* from_mat = from_type->As<sem::Matrix>();
-        auto* to_mat = to_type->As<sem::Matrix>();
+        auto* from_mat = from_type->As<type::Matrix>();
+        auto* to_mat = to_type->As<type::Matrix>();
         if (from_mat == to_mat) {
             return val_id;
         }
@@ -1700,8 +1700,8 @@
             auto val = constant->As<u32>();
             return GenerateConstantIfNeeded(ScalarConstant::U32(val.value));
         },
-        [&](const sem::Vector* v) { return composite(v->Width()); },
-        [&](const sem::Matrix* m) { return composite(m->columns()); },
+        [&](const type::Vector* v) { return composite(v->Width()); },
+        [&](const type::Matrix* m) { return composite(m->columns()); },
         [&](const sem::Array* a) {
             auto count = a->ConstantCount();
             if (!count) {
@@ -1803,7 +1803,7 @@
     });
 }
 
-uint32_t Builder::GenerateConstantVectorSplatIfNeeded(const sem::Vector* type, uint32_t value_id) {
+uint32_t Builder::GenerateConstantVectorSplatIfNeeded(const type::Vector* type, uint32_t value_id) {
     auto type_id = GenerateTypeIfNeeded(type);
     if (type_id == 0 || value_id == 0) {
         return 0;
@@ -1912,7 +1912,7 @@
     OperandList ops;
     ops.push_back(Operand(GenerateTypeIfNeeded(vec_type)));
     ops.push_back(splat_result);
-    for (size_t i = 0; i < vec_type->As<sem::Vector>()->Width(); ++i) {
+    for (size_t i = 0; i < vec_type->As<type::Vector>()->Width(); ++i) {
         ops.push_back(Operand(scalar_id));
     }
     if (!push_function_inst(spv::Op::OpCompositeConstruct, ops)) {
@@ -1924,7 +1924,7 @@
 
 uint32_t Builder::GenerateMatrixAddOrSub(uint32_t lhs_id,
                                          uint32_t rhs_id,
-                                         const sem::Matrix* type,
+                                         const type::Matrix* type,
                                          spv::Op op) {
     // Example addition of two matrices:
     // %31 = OpLoad %mat3v4float %m34
@@ -1940,7 +1940,7 @@
     // %41 = OpFAdd %v4float %39 %40
     // %42 = OpCompositeConstruct %mat3v4float %35 %38 %41
 
-    auto* column_type = builder_.create<sem::Vector>(type->type(), type->rows());
+    auto* column_type = builder_.create<type::Vector>(type->type(), type->rows());
     auto column_type_id = GenerateTypeIfNeeded(column_type);
 
     OperandList ops;
@@ -2015,8 +2015,8 @@
     // Handle matrix-matrix addition and subtraction
     if ((expr->IsAdd() || expr->IsSubtract()) && lhs_type->is_float_matrix() &&
         rhs_type->is_float_matrix()) {
-        auto* lhs_mat = lhs_type->As<sem::Matrix>();
-        auto* rhs_mat = rhs_type->As<sem::Matrix>();
+        auto* lhs_mat = lhs_type->As<type::Matrix>();
+        auto* rhs_mat = rhs_type->As<type::Matrix>();
 
         // This should already have been validated by resolver
         if (lhs_mat->rows() != rhs_mat->rows() || lhs_mat->columns() != rhs_mat->columns()) {
@@ -2035,7 +2035,7 @@
                                (lhs_type->is_float_vector() && rhs_type->is_float_scalar()));
 
     if (expr->IsArithmetic() && !is_float_scalar_vector_multiply) {
-        if (lhs_type->Is<sem::Vector>() && rhs_type->is_numeric_scalar()) {
+        if (lhs_type->Is<type::Vector>() && rhs_type->is_numeric_scalar()) {
             uint32_t splat_vector_id = GenerateSplat(rhs_id, lhs_type);
             if (splat_vector_id == 0) {
                 return 0;
@@ -2043,7 +2043,7 @@
             rhs_id = splat_vector_id;
             rhs_type = lhs_type;
 
-        } else if (lhs_type->is_numeric_scalar() && rhs_type->Is<sem::Vector>()) {
+        } else if (lhs_type->is_numeric_scalar() && rhs_type->Is<type::Vector>()) {
             uint32_t splat_vector_id = GenerateSplat(lhs_id, rhs_type);
             if (splat_vector_id == 0) {
                 return 0;
@@ -2404,7 +2404,7 @@
             break;
         case BuiltinType::kDot: {
             op = spv::Op::OpDot;
-            auto* vec_ty = builtin->Parameters()[0]->Type()->As<sem::Vector>();
+            auto* vec_ty = builtin->Parameters()[0]->Type()->As<type::Vector>();
             if (vec_ty->type()->is_integer_scalar()) {
                 // TODO(crbug.com/tint/1267): OpDot requires floating-point types, but
                 // WGSL also supports integer types. SPV_KHR_integer_dot_product adds
@@ -2490,7 +2490,7 @@
 
             // If the interpolant is scalar but the objects are vectors, we need to
             // splat the interpolant into a vector of the same size.
-            auto* result_vector_type = builtin->ReturnType()->As<sem::Vector>();
+            auto* result_vector_type = builtin->ReturnType()->As<type::Vector>();
             if (result_vector_type && builtin->Parameters()[2]->Type()->is_scalar()) {
                 f_id = GenerateSplat(f_id, builtin->Parameters()[0]->Type());
                 if (f_id == 0) {
@@ -2523,10 +2523,10 @@
             // If the condition is scalar but the objects are vectors, we need to
             // splat the condition into a vector of the same size.
             // TODO(jrprice): If we're targeting SPIR-V 1.4, we don't need to do this.
-            auto* result_vector_type = builtin->ReturnType()->As<sem::Vector>();
+            auto* result_vector_type = builtin->ReturnType()->As<type::Vector>();
             if (result_vector_type && builtin->Parameters()[2]->Type()->is_scalar()) {
-                auto* bool_vec_ty = builder_.create<sem::Vector>(builder_.create<type::Bool>(),
-                                                                 result_vector_type->Width());
+                auto* bool_vec_ty = builder_.create<type::Vector>(builder_.create<type::Bool>(),
+                                                                  result_vector_type->Width());
                 if (!GenerateTypeIfNeeded(bool_vec_ty)) {
                     return 0;
                 }
@@ -2687,7 +2687,7 @@
     auto append_result_type_and_id_to_spirv_params_for_read = [&]() {
         if (texture_type->IsAnyOf<type::DepthTexture, type::DepthMultisampledTexture>()) {
             auto* f32 = builder_.create<type::F32>();
-            auto* spirv_result_type = builder_.create<sem::Vector>(f32, 4u);
+            auto* spirv_result_type = builder_.create<type::Vector>(f32, 4u);
             auto spirv_result = result_op();
             post_emission = [=] {
                 return push_function_inst(spv::Op::OpCompositeExtract,
@@ -2718,7 +2718,7 @@
             auto* element_type = ElementTypeOf(call->Type());
             auto spirv_result = result_op();
             auto* spirv_result_type =
-                builder_.create<sem::Vector>(element_type, spirv_result_width);
+                builder_.create<type::Vector>(element_type, spirv_result_width);
             if (swizzle.size() > 1) {
                 post_emission = [=] {
                     OperandList operands{
@@ -3692,7 +3692,7 @@
                 push_type(spv::Op::OpTypeInt, {result, Operand(32u), Operand(1u)});
                 return true;
             },
-            [&](const sem::Matrix* mat) {  //
+            [&](const type::Matrix* mat) {  //
                 return GenerateMatrixType(mat, result);
             },
             [&](const type::Pointer* ptr) {  //
@@ -3708,7 +3708,7 @@
                 push_type(spv::Op::OpTypeInt, {result, Operand(32u), Operand(0u)});
                 return true;
             },
-            [&](const sem::Vector* vec) {  //
+            [&](const type::Vector* vec) {  //
                 return GenerateVectorType(vec, result);
             },
             [&](const type::Void*) {
@@ -3867,8 +3867,8 @@
     return true;
 }
 
-bool Builder::GenerateMatrixType(const sem::Matrix* mat, const Operand& result) {
-    auto* col_type = builder_.create<sem::Vector>(mat->type(), mat->rows());
+bool Builder::GenerateMatrixType(const type::Matrix* mat, const Operand& result) {
+    auto* col_type = builder_.create<type::Vector>(mat->type(), mat->rows());
     auto col_type_id = GenerateTypeIfNeeded(col_type);
     if (has_error()) {
         return false;
@@ -3972,7 +3972,7 @@
     return GenerateTypeIfNeeded(member->Type());
 }
 
-bool Builder::GenerateVectorType(const sem::Vector* vec, const Operand& result) {
+bool Builder::GenerateVectorType(const type::Vector* vec, const Operand& result) {
     auto type_id = GenerateTypeIfNeeded(vec->type());
     if (has_error()) {
         return false;
diff --git a/src/tint/writer/spirv/builder.h b/src/tint/writer/spirv/builder.h
index c5b07ce..2f33002 100644
--- a/src/tint/writer/spirv/builder.h
+++ b/src/tint/writer/spirv/builder.h
@@ -485,7 +485,7 @@
     /// @param mat the matrix to generate
     /// @param result the result operand
     /// @returns true if the matrix was successfully generated
-    bool GenerateMatrixType(const sem::Matrix* mat, const Operand& result);
+    bool GenerateMatrixType(const type::Matrix* mat, const Operand& result);
     /// Generates a pointer type declaration
     /// @param ptr the pointer type to generate
     /// @param result the result operand
@@ -517,7 +517,7 @@
     /// @param vec the vector to generate
     /// @param result the result operand
     /// @returns true if the vector was successfully generated
-    bool GenerateVectorType(const sem::Vector* vec, const Operand& result);
+    bool GenerateVectorType(const type::Vector* vec, const Operand& result);
 
     /// Generates instructions to splat `scalar_id` into a vector of type
     /// `vec_type`
@@ -534,7 +534,7 @@
     /// @returns id of the result matrix
     uint32_t GenerateMatrixAddOrSub(uint32_t lhs_id,
                                     uint32_t rhs_id,
-                                    const sem::Matrix* type,
+                                    const type::Matrix* type,
                                     spv::Op op);
 
     /// Converts TexelFormat to SPIR-V and pushes an appropriate capability.
@@ -575,7 +575,7 @@
     /// @param type the type of the vector to generate
     /// @param value_id the ID of the scalar value to splat
     /// @returns the ID on success or 0 on failure
-    uint32_t GenerateConstantVectorSplatIfNeeded(const sem::Vector* type, uint32_t value_id);
+    uint32_t GenerateConstantVectorSplatIfNeeded(const type::Vector* type, uint32_t value_id);
 
     /// Registers the semantic variable to the given SPIR-V ID
     /// @param var the semantic variable
diff --git a/src/tint/writer/spirv/builder_entry_point_test.cc b/src/tint/writer/spirv/builder_entry_point_test.cc
index 3527ea9..a064ee3 100644
--- a/src/tint/writer/spirv/builder_entry_point_test.cc
+++ b/src/tint/writer/spirv/builder_entry_point_test.cc
@@ -23,8 +23,8 @@
 #include "src/tint/ast/stage_attribute.h"
 #include "src/tint/ast/variable.h"
 #include "src/tint/program.h"
-#include "src/tint/sem/vector.h"
 #include "src/tint/type/f32.h"
+#include "src/tint/type/vector.h"
 #include "src/tint/writer/spirv/builder.h"
 #include "src/tint/writer/spirv/spv_dump.h"
 #include "src/tint/writer/spirv/test_helper.h"
diff --git a/src/tint/writer/spirv/builder_type_test.cc b/src/tint/writer/spirv/builder_type_test.cc
index ef632a1..d698593 100644
--- a/src/tint/writer/spirv/builder_type_test.cc
+++ b/src/tint/writer/spirv/builder_type_test.cc
@@ -227,8 +227,8 @@
 
 TEST_F(BuilderTest_Type, GenerateMatrix) {
     auto* f32 = create<type::F32>();
-    auto* vec3 = create<sem::Vector>(f32, 3u);
-    auto* mat2x3 = create<sem::Matrix>(vec3, 2u);
+    auto* vec3 = create<type::Vector>(f32, 3u);
+    auto* mat2x3 = create<type::Matrix>(vec3, 2u);
 
     spirv::Builder& b = Build();
 
@@ -245,8 +245,8 @@
 
 TEST_F(BuilderTest_Type, ReturnsGeneratedMatrix) {
     auto* i32 = create<type::I32>();
-    auto* col = create<sem::Vector>(i32, 4u);
-    auto* mat = create<sem::Matrix>(col, 3u);
+    auto* col = create<type::Vector>(i32, 4u);
+    auto* mat = create<type::Matrix>(col, 3u);
 
     spirv::Builder& b = Build();
 
@@ -260,8 +260,8 @@
 
 TEST_F(BuilderTest_Type, GenerateF16Matrix) {
     auto* f16 = create<type::F16>();
-    auto* vec3 = create<sem::Vector>(f16, 3u);
-    auto* mat2x3 = create<sem::Matrix>(vec3, 2u);
+    auto* vec3 = create<type::Vector>(f16, 3u);
+    auto* mat2x3 = create<type::Matrix>(vec3, 2u);
 
     spirv::Builder& b = Build();
 
@@ -278,8 +278,8 @@
 
 TEST_F(BuilderTest_Type, ReturnsGeneratedF16Matrix) {
     auto* f16 = create<type::F16>();
-    auto* col = create<sem::Vector>(f16, 4u);
-    auto* mat = create<sem::Matrix>(col, 3u);
+    auto* col = create<type::Vector>(f16, 4u);
+    auto* mat = create<type::Matrix>(col, 3u);
 
     spirv::Builder& b = Build();
 
@@ -545,7 +545,7 @@
 }
 
 TEST_F(BuilderTest_Type, GenerateVector) {
-    auto* vec = create<sem::Vector>(create<type::F32>(), 3u);
+    auto* vec = create<type::Vector>(create<type::F32>(), 3u);
 
     spirv::Builder& b = Build();
 
@@ -561,7 +561,7 @@
 
 TEST_F(BuilderTest_Type, ReturnsGeneratedVector) {
     auto* i32 = create<type::I32>();
-    auto* vec = create<sem::Vector>(i32, 3u);
+    auto* vec = create<type::Vector>(i32, 3u);
 
     spirv::Builder& b = Build();