Switch ResourceTable to use ResourceNamedType instead of ResourceType.

DD: go/custom-resource-types-in-aapt2

Bug: b/215108200
Test: existing
Change-Id: If9ddcd529dff66c8ec4238f56ab64391c2f44c28
diff --git a/tools/aapt2/Debug.cpp b/tools/aapt2/Debug.cpp
index f47d66e..41896f6 100644
--- a/tools/aapt2/Debug.cpp
+++ b/tools/aapt2/Debug.cpp
@@ -273,7 +273,7 @@
     printer->Indent();
     for (const auto& type : package.types) {
       printer->Print("type ");
-      printer->Print(to_string(type.type));
+      printer->Print(type.named_type.to_string());
       if (type.id) {
         printer->Print(StringPrintf(" id=%02x", type.id.value()));
       }
@@ -287,7 +287,7 @@
         printer->Print(" ");
 
         // Write the name without the package (this is obvious and too verbose).
-        printer->Print(to_string(type.type));
+        printer->Print(type.named_type.to_string());
         printer->Print("/");
         printer->Print(entry.name);
 
@@ -547,7 +547,7 @@
           const auto policy_subsection = StringPrintf(R"(policies="%s")",
               android::idmap2::policy::PoliciesToDebugString(overlayable_item.policies).c_str());
           const auto value =
-            StringPrintf("%s/%s", to_string(type->type).data(), entry->name.c_str());
+              StringPrintf("%s/%s", type->named_type.to_string().data(), entry->name.c_str());
           items.push_back(DumpOverlayableEntry{overlayable_section, policy_subsection, value});
         }
       }
diff --git a/tools/aapt2/ResourceTable.cpp b/tools/aapt2/ResourceTable.cpp
index 98cce26..0f5118d 100644
--- a/tools/aapt2/ResourceTable.cpp
+++ b/tools/aapt2/ResourceTable.cpp
@@ -43,8 +43,9 @@
 const char* Overlayable::kActorScheme = "overlay";
 
 namespace {
-bool less_than_type(const std::unique_ptr<ResourceTableType>& lhs, ResourceType rhs) {
-  return lhs->type < rhs;
+bool less_than_type(const std::unique_ptr<ResourceTableType>& lhs,
+                    const ResourceNamedTypeRef& rhs) {
+  return lhs->named_type < rhs;
 }
 
 template <typename T>
@@ -115,18 +116,24 @@
 }
 
 template <typename Func, typename Elements>
-static ResourceTableType* FindTypeRunAction(ResourceType type, Elements& entries, Func action) {
+static ResourceTableType* FindTypeRunAction(const ResourceNamedTypeRef& type, Elements& entries,
+                                            Func action) {
   const auto iter = std::lower_bound(entries.begin(), entries.end(), type, less_than_type);
-  const bool found = iter != entries.end() && type == (*iter)->type;
+  const bool found = iter != entries.end() && type == (*iter)->named_type;
   return action(found, iter);
 }
 
-ResourceTableType* ResourceTablePackage::FindType(ResourceType type) const {
+ResourceTableType* ResourceTablePackage::FindTypeWithDefaultName(const ResourceType type) const {
+  auto named_type = ResourceNamedTypeWithDefaultName(type);
+  return FindType(named_type);
+}
+
+ResourceTableType* ResourceTablePackage::FindType(const ResourceNamedTypeRef& type) const {
   return FindTypeRunAction(type, types,
                            [&](bool found, auto& iter) { return found ? iter->get() : nullptr; });
 }
 
-ResourceTableType* ResourceTablePackage::FindOrCreateType(ResourceType type) {
+ResourceTableType* ResourceTablePackage::FindOrCreateType(const ResourceNamedTypeRef& type) {
   return FindTypeRunAction(type, types, [&](bool found, auto& iter) {
     return found ? iter->get() : types.emplace(iter, new ResourceTableType(type))->get();
   });
@@ -329,7 +336,7 @@
 
 struct TypeViewComparer {
   bool operator()(const ResourceTableTypeView& lhs, const ResourceTableTypeView& rhs) {
-    return lhs.id != rhs.id ? lhs.id < rhs.id : lhs.type < rhs.type;
+    return lhs.id != rhs.id ? lhs.id < rhs.id : lhs.named_type < rhs.named_type;
   }
 };
 
@@ -355,7 +362,8 @@
                                        id ? id.value().package_id() : std::optional<uint8_t>{}};
   auto view_package = package_inserter.Insert(table.packages, std::move(new_package));
 
-  ResourceTableTypeView new_type{type->type, id ? id.value().type_id() : std::optional<uint8_t>{}};
+  ResourceTableTypeView new_type{type->named_type,
+                                 id ? id.value().type_id() : std::optional<uint8_t>{}};
   auto view_type = type_inserter.Insert(view_package->types, std::move(new_type));
 
   if (visibility.level == Visibility::Level::kPublic) {
@@ -420,13 +428,14 @@
     // we can reuse those packages for other types that need to be extracted from this package.
     // `start_index` is the index of the first newly created package that can be reused.
     const size_t start_index = new_packages.size();
-    std::map<ResourceType, size_t> type_new_package_index;
+    std::map<ResourceNamedType, size_t> type_new_package_index;
     for (auto type_it = package.types.begin(); type_it != package.types.end();) {
       auto& type = *type_it;
-      auto type_index_iter = type_new_package_index.find(type.type);
+      auto type_index_iter = type_new_package_index.find(type.named_type);
       if (type_index_iter == type_new_package_index.end()) {
         // First occurrence of the resource type in this package. Keep it in this package.
-        type_new_package_index.insert(type_index_iter, std::make_pair(type.type, start_index));
+        type_new_package_index.insert(type_index_iter,
+                                      std::make_pair(type.named_type, start_index));
         ++type_it;
         continue;
       }
@@ -440,7 +449,7 @@
 
       // Move the type into a new package
       auto& other_package = new_packages[index];
-      type_new_package_index[type.type] = index + 1;
+      type_new_package_index[type.named_type] = index + 1;
       type_inserter.Insert(other_package.types, std::move(type));
       type_it = package.types.erase(type_it);
     }
@@ -473,7 +482,7 @@
   }
 
   auto package = FindOrCreatePackage(res.name.package);
-  auto type = package->FindOrCreateType(res.name.type.type);
+  auto type = package->FindOrCreateType(res.name.type);
   auto entry_it = std::equal_range(type->entries.begin(), type->entries.end(), res.name.entry,
                                    NameEqualRange<ResourceEntry>{});
   const size_t entry_count = std::distance(entry_it.first, entry_it.second);
@@ -593,7 +602,7 @@
     return {};
   }
 
-  ResourceTableType* type = package->FindType(name.type.type);
+  ResourceTableType* type = package->FindType(name.type);
   if (type == nullptr) {
     return {};
   }
@@ -612,7 +621,7 @@
     return {};
   }
 
-  ResourceTableType* type = package->FindType(name.type.type);
+  ResourceTableType* type = package->FindType(name.type);
   if (type == nullptr) {
     return {};
   }
@@ -633,7 +642,7 @@
     return {};
   }
 
-  ResourceTableType* type = package->FindType(name.type.type);
+  ResourceTableType* type = package->FindType(name.type);
   if (type == nullptr) {
     return {};
   }
@@ -655,7 +664,7 @@
   for (const auto& pkg : packages) {
     ResourceTablePackage* new_pkg = new_table->FindOrCreatePackage(pkg->name);
     for (const auto& type : pkg->types) {
-      ResourceTableType* new_type = new_pkg->FindOrCreateType(type->type);
+      ResourceTableType* new_type = new_pkg->FindOrCreateType(type->named_type);
       new_type->visibility_level = type->visibility_level;
 
       for (const auto& entry : type->entries) {
diff --git a/tools/aapt2/ResourceTable.h b/tools/aapt2/ResourceTable.h
index 2e17659..7aa8b0f 100644
--- a/tools/aapt2/ResourceTable.h
+++ b/tools/aapt2/ResourceTable.h
@@ -168,7 +168,7 @@
 class ResourceTableType {
  public:
   // The logical type of resource (string, drawable, layout, etc.).
-  const ResourceType type;
+  const ResourceNamedType named_type;
 
   // Whether this type is public (and must maintain the same type ID across builds).
   Visibility::Level visibility_level = Visibility::Level::kUndefined;
@@ -176,7 +176,9 @@
   // List of resources for this type.
   std::vector<std::unique_ptr<ResourceEntry>> entries;
 
-  explicit ResourceTableType(const ResourceType type) : type(type) {}
+  explicit ResourceTableType(const ResourceNamedTypeRef& type)
+      : named_type(type.ToResourceNamedType()) {
+  }
 
   ResourceEntry* CreateEntry(const android::StringPiece& name);
   ResourceEntry* FindEntry(const android::StringPiece& name) const;
@@ -196,8 +198,9 @@
   }
 
   ResourceTablePackage() = default;
-  ResourceTableType* FindType(ResourceType type) const;
-  ResourceTableType* FindOrCreateType(ResourceType type);
+  ResourceTableType* FindTypeWithDefaultName(const ResourceType type) const;
+  ResourceTableType* FindType(const ResourceNamedTypeRef& type) const;
+  ResourceTableType* FindOrCreateType(const ResourceNamedTypeRef& type);
 
  private:
   DISALLOW_COPY_AND_ASSIGN(ResourceTablePackage);
@@ -217,7 +220,7 @@
 };
 
 struct ResourceTableTypeView {
-  ResourceType type;
+  ResourceNamedType named_type;
   std::optional<uint8_t> id;
   Visibility::Level visibility_level = Visibility::Level::kUndefined;
 
diff --git a/tools/aapt2/cmd/Compile.cpp b/tools/aapt2/cmd/Compile.cpp
index fe56018..e27b9aa 100644
--- a/tools/aapt2/cmd/Compile.cpp
+++ b/tools/aapt2/cmd/Compile.cpp
@@ -243,9 +243,9 @@
                 r_txt_printer.Print("private ");
             }
 
-            if (type->type != ResourceType::kStyleable) {
+            if (type->named_type.type != ResourceType::kStyleable) {
               r_txt_printer.Print("int ");
-              r_txt_printer.Print(to_string(type->type));
+              r_txt_printer.Print(type->named_type.to_string());
               r_txt_printer.Print(" ");
               r_txt_printer.Println(entry->name);
             } else {
diff --git a/tools/aapt2/cmd/Diff.cpp b/tools/aapt2/cmd/Diff.cpp
index d9e8c92..a854146 100644
--- a/tools/aapt2/cmd/Diff.cpp
+++ b/tools/aapt2/cmd/Diff.cpp
@@ -105,7 +105,7 @@
   Value* value_b = config_value_b->value.get();
   if (!value_a->Equals(value_b)) {
     std::stringstream str_stream;
-    str_stream << "value " << pkg_a.name << ":" << type_a.type << "/" << entry_a.name
+    str_stream << "value " << pkg_a.name << ":" << type_a.named_type << "/" << entry_a.name
                << " config=" << config_value_a->config << " does not match:\n";
     value_a->Print(&str_stream);
     str_stream << "\n vs \n";
@@ -128,7 +128,7 @@
     auto config_value_b = entry_b.FindValue(config_value_a->config);
     if (!config_value_b) {
       std::stringstream str_stream;
-      str_stream << "missing " << pkg_a.name << ":" << type_a.type << "/" << entry_a.name
+      str_stream << "missing " << pkg_a.name << ":" << type_a.named_type << "/" << entry_a.name
                  << " config=" << config_value_a->config;
       EmitDiffLine(apk_b->GetSource(), str_stream.str());
       diff = true;
@@ -143,7 +143,7 @@
     auto config_value_a = entry_a.FindValue(config_value_b->config);
     if (!config_value_a) {
       std::stringstream str_stream;
-      str_stream << "new config " << pkg_b.name << ":" << type_b.type << "/" << entry_b.name
+      str_stream << "new config " << pkg_b.name << ":" << type_b.named_type << "/" << entry_b.name
                  << " config=" << config_value_b->config;
       EmitDiffLine(apk_b->GetSource(), str_stream.str());
       diff = true;
@@ -164,13 +164,15 @@
     if (entry_b_iter == type_b.entries.end()) {
       // Type A contains a type that type B does not have.
       std::stringstream str_stream;
-      str_stream << "missing " << pkg_a.name << ":" << type_a.type << "/" << entry_a_iter->name;
+      str_stream << "missing " << pkg_a.name << ":" << type_a.named_type << "/"
+                 << entry_a_iter->name;
       EmitDiffLine(apk_a->GetSource(), str_stream.str());
       diff = true;
     } else if (entry_a_iter == type_a.entries.end()) {
       // Type B contains a type that type A does not have.
       std::stringstream str_stream;
-      str_stream << "new entry " << pkg_b.name << ":" << type_b.type << "/" << entry_b_iter->name;
+      str_stream << "new entry " << pkg_b.name << ":" << type_b.named_type << "/"
+                 << entry_b_iter->name;
       EmitDiffLine(apk_b->GetSource(), str_stream.str());
       diff = true;
     } else {
@@ -178,7 +180,7 @@
       const auto& entry_b = *entry_b_iter;
       if (IsSymbolVisibilityDifferent(entry_a.visibility, entry_b.visibility)) {
         std::stringstream str_stream;
-        str_stream << pkg_a.name << ":" << type_a.type << "/" << entry_a.name
+        str_stream << pkg_a.name << ":" << type_a.named_type << "/" << entry_a.name
                    << " has different visibility (";
         if (entry_b.visibility.staged_api) {
           str_stream << "STAGED ";
@@ -203,7 +205,7 @@
       } else if (IsIdDiff(entry_a.visibility.level, entry_a.id, entry_b.visibility.level,
                           entry_b.id)) {
         std::stringstream str_stream;
-        str_stream << pkg_a.name << ":" << type_a.type << "/" << entry_a.name
+        str_stream << pkg_a.name << ":" << type_a.named_type << "/" << entry_a.name
                    << " has different public ID (";
         if (entry_b.id) {
           str_stream << "0x" << std::hex << entry_b.id.value();
@@ -243,13 +245,13 @@
     if (type_b_iter == pkg_b.types.end()) {
       // Type A contains a type that type B does not have.
       std::stringstream str_stream;
-      str_stream << "missing " << pkg_a.name << ":" << type_a_iter->type;
+      str_stream << "missing " << pkg_a.name << ":" << type_a_iter->named_type;
       EmitDiffLine(apk_a->GetSource(), str_stream.str());
       diff = true;
     } else if (type_a_iter == pkg_a.types.end()) {
       // Type B contains a type that type A does not have.
       std::stringstream str_stream;
-      str_stream << "new type " << pkg_b.name << ":" << type_b_iter->type;
+      str_stream << "new type " << pkg_b.name << ":" << type_b_iter->named_type;
       EmitDiffLine(apk_b->GetSource(), str_stream.str());
       diff = true;
     } else {
@@ -257,7 +259,7 @@
       const auto& type_b = *type_b_iter;
       if (type_a.visibility_level != type_b.visibility_level) {
         std::stringstream str_stream;
-        str_stream << pkg_a.name << ":" << type_a.type << " has different visibility (";
+        str_stream << pkg_a.name << ":" << type_a.named_type << " has different visibility (";
         if (type_b.visibility_level == Visibility::Level::kPublic) {
           str_stream << "PUBLIC";
         } else {
@@ -274,7 +276,7 @@
         diff = true;
       } else if (IsIdDiff(type_a.visibility_level, type_a.id, type_b.visibility_level, type_b.id)) {
         std::stringstream str_stream;
-        str_stream << pkg_a.name << ":" << type_a.type << " has different public ID (";
+        str_stream << pkg_a.name << ":" << type_a.named_type << " has different public ID (";
         if (type_b.id) {
           str_stream << "0x" << std::hex << type_b.id.value();
         } else {
diff --git a/tools/aapt2/cmd/Link.cpp b/tools/aapt2/cmd/Link.cpp
index 1efe6c2..bd74cc7 100644
--- a/tools/aapt2/cmd/Link.cpp
+++ b/tools/aapt2/cmd/Link.cpp
@@ -556,7 +556,7 @@
           file_op.config = config_value->config;
           file_op.file_to_copy = file;
 
-          if (type->type != ResourceType::kRaw &&
+          if (type->named_type.type != ResourceType::kRaw &&
               (file_ref->type == ResourceFile::Type::kBinaryXml ||
                file_ref->type == ResourceFile::Type::kProtoXml)) {
             std::unique_ptr<io::IData> data = file->OpenAsData();
@@ -596,7 +596,8 @@
 
             file_op.xml_to_flatten->file.config = config_value->config;
             file_op.xml_to_flatten->file.source = file_ref->GetSource();
-            file_op.xml_to_flatten->file.name = ResourceName(pkg->name, type->type, entry->name);
+            file_op.xml_to_flatten->file.name =
+                ResourceName(pkg->name, type->named_type, entry->name);
           }
 
           // NOTE(adamlesinski): Explicitly construct a StringPiece here, or
@@ -1009,7 +1010,7 @@
         // We have a package that is not related to the one we're building!
         for (const auto& type : package->types) {
           for (const auto& entry : type->entries) {
-            ResourceNameRef res_name(package->name, type->type, entry->name);
+            ResourceNameRef res_name(package->name, type->named_type, entry->name);
 
             for (const auto& config_value : entry->values) {
               // Special case the occurrence of an ID that is being generated
@@ -1046,7 +1047,7 @@
       for (const auto& type : package->types) {
         for (const auto& entry : type->entries) {
           if (entry->id) {
-            ResourceNameRef res_name(package->name, type->type, entry->name);
+            ResourceNameRef res_name(package->name, type->named_type, entry->name);
             context_->GetDiagnostics()->Error(DiagMessage() << "resource " << res_name << " has ID "
                                                             << entry->id.value() << " assigned");
             return false;
@@ -2016,7 +2017,7 @@
         for (auto& package : final_table_.packages) {
           for (auto& type : package->types) {
             for (auto& entry : type->entries) {
-              ResourceName name(package->name, type->type, entry->name);
+              ResourceName name(package->name, type->named_type, entry->name);
               // The IDs are guaranteed to exist.
               options_.stable_id_map[std::move(name)] = entry->id.value();
             }
diff --git a/tools/aapt2/cmd/Optimize.cpp b/tools/aapt2/cmd/Optimize.cpp
index caa3e60..e1370fd 100644
--- a/tools/aapt2/cmd/Optimize.cpp
+++ b/tools/aapt2/cmd/Optimize.cpp
@@ -254,7 +254,7 @@
             }
 
             if (file_ref->file == nullptr) {
-              ResourceNameRef name(pkg->name, type->type, entry->name);
+              ResourceNameRef name(pkg->name, type->named_type, entry->name);
               context_->GetDiagnostics()->Warn(DiagMessage(file_ref->GetSource())
                                                << "file for resource " << name << " with config '"
                                                << config_value->config << "' not found");
diff --git a/tools/aapt2/compile/IdAssigner.cpp b/tools/aapt2/compile/IdAssigner.cpp
index fa816be..29f9a08 100644
--- a/tools/aapt2/compile/IdAssigner.cpp
+++ b/tools/aapt2/compile/IdAssigner.cpp
@@ -128,7 +128,7 @@
   for (auto& package : table->packages) {
     for (auto& type : package->types) {
       for (auto& entry : type->entries) {
-        const ResourceName name(package->name, type->type, entry->name);
+        const ResourceName name(package->name, type->named_type, entry->name);
         if (entry->id && !assigned_ids.ReserveId(name, entry->id.value(), entry->visibility,
                                                  context->GetDiagnostics())) {
           return false;
@@ -175,7 +175,7 @@
   for (auto& package : table->packages) {
     for (auto& type : package->types) {
       for (auto& entry : type->entries) {
-        const ResourceName name(package->name, type->type, entry->name);
+        const ResourceName name(package->name, type->named_type, entry->name);
         if (entry->id) {
           continue;
         }
diff --git a/tools/aapt2/compile/IdAssigner_test.cpp b/tools/aapt2/compile/IdAssigner_test.cpp
index d357571..8911dad 100644
--- a/tools/aapt2/compile/IdAssigner_test.cpp
+++ b/tools/aapt2/compile/IdAssigner_test.cpp
@@ -191,12 +191,12 @@
       for (auto& entry : type->entries) {
         if (!entry->id) {
           return ::testing::AssertionFailure()
-                 << "resource " << ResourceNameRef(package->name, type->type, entry->name)
+                 << "resource " << ResourceNameRef(package->name, type->named_type, entry->name)
                  << " has no ID";
         }
         if (!seen_ids.insert(entry->id.value()).second) {
           return ::testing::AssertionFailure()
-                 << "resource " << ResourceNameRef(package->name, type->type, entry->name)
+                 << "resource " << ResourceNameRef(package->name, type->named_type, entry->name)
                  << " has a non-unique ID" << std::hex << entry->id.value() << std::dec;
         }
       }
diff --git a/tools/aapt2/format/binary/TableFlattener.cpp b/tools/aapt2/format/binary/TableFlattener.cpp
index a9192e8..b97f1c5 100644
--- a/tools/aapt2/format/binary/TableFlattener.cpp
+++ b/tools/aapt2/format/binary/TableFlattener.cpp
@@ -360,7 +360,7 @@
       if (!FlattenValue(&flat_entry, &values_buffer)) {
         diag_->Error(DiagMessage()
                      << "failed to flatten resource '"
-                     << ResourceNameRef(package_.name, type.type, flat_entry.entry->name)
+                     << ResourceNameRef(package_.name, type.named_type, flat_entry.entry->name)
                      << "' for configuration '" << config << "'");
         return false;
       }
@@ -447,7 +447,7 @@
         ResourceId id = android::make_resid(package_.id.value(), type.id.value(), entry.id.value());
         CHECK(seen_ids.find(id) == seen_ids.end())
             << "multiple overlayable definitions found for resource "
-            << ResourceName(package_.name, type.type, entry.name).to_string();
+            << ResourceName(package_.name, type.named_type, entry.name).to_string();
         seen_ids.insert(id);
 
         // Find the overlayable chunk with the specified name
@@ -592,7 +592,8 @@
   bool FlattenTypes(BigBuffer* buffer) {
     size_t expected_type_id = 1;
     for (const ResourceTableTypeView& type : package_.types) {
-      if (type.type == ResourceType::kStyleable || type.type == ResourceType::kMacro) {
+      if (type.named_type.type == ResourceType::kStyleable ||
+          type.named_type.type == ResourceType::kMacro) {
         // Styleables and macros are not real resource types.
         continue;
       }
@@ -606,7 +607,7 @@
         expected_type_id++;
       }
       expected_type_id++;
-      type_pool_.MakeRef(to_string(type.type));
+      type_pool_.MakeRef(to_string(type.named_type.type));
 
       if (!FlattenTypeSpec(type, type.entries, buffer)) {
         return false;
@@ -634,7 +635,7 @@
         }
 
         uint32_t local_key_index;
-        ResourceName resource_name({}, type.type, entry.name);
+        ResourceName resource_name({}, type.named_type, entry.name);
         if (!collapse_key_stringpool_ ||
             name_collapse_exemptions_.find(resource_name) != name_collapse_exemptions_.end()) {
           local_key_index = (uint32_t)key_pool_.MakeRef(entry.name).index();
diff --git a/tools/aapt2/format/proto/ProtoDeserialize.cpp b/tools/aapt2/format/proto/ProtoDeserialize.cpp
index 236c381..475f393 100644
--- a/tools/aapt2/format/proto/ProtoDeserialize.cpp
+++ b/tools/aapt2/format/proto/ProtoDeserialize.cpp
@@ -437,7 +437,8 @@
       return false;
     }
 
-    ResourceTableType* type = pkg->FindOrCreateType(*res_type);
+    auto named_type = ResourceNamedTypeWithDefaultName(*res_type);
+    ResourceTableType* type = pkg->FindOrCreateType(named_type);
 
     for (const pb::Entry& pb_entry : pb_type.entry()) {
       ResourceEntry* entry = type->CreateEntry(pb_entry.name());
@@ -515,7 +516,7 @@
       ResourceId resid(pb_package.package_id().id(), pb_type.type_id().id(),
                        pb_entry.entry_id().id());
       if (resid.is_valid()) {
-        id_index[resid] = ResourceNameRef(pkg->name, type->type, entry->name);
+        id_index[resid] = ResourceNameRef(pkg->name, type->named_type, entry->name);
       }
 
       for (const pb::ConfigValue& pb_config_value : pb_entry.config_value()) {
diff --git a/tools/aapt2/format/proto/ProtoSerialize.cpp b/tools/aapt2/format/proto/ProtoSerialize.cpp
index f3b7f75..2481478 100644
--- a/tools/aapt2/format/proto/ProtoSerialize.cpp
+++ b/tools/aapt2/format/proto/ProtoSerialize.cpp
@@ -358,7 +358,7 @@
       if (type.id) {
         pb_type->mutable_type_id()->set_id(type.id.value());
       }
-      pb_type->set_name(to_string(type.type).to_string());
+      pb_type->set_name(to_string(type.named_type.type).to_string());
 
       // hardcoded string uses characters which make it an invalid resource name
       static const char* obfuscated_resource_name = "0_resource_name_obfuscated";
@@ -367,7 +367,7 @@
         if (entry.id) {
           pb_entry->mutable_entry_id()->set_id(entry.id.value());
         }
-        ResourceName resource_name({}, type.type, entry.name);
+        ResourceName resource_name({}, type.named_type, entry.name);
         if (options.collapse_key_stringpool &&
             options.name_collapse_exemptions.find(resource_name) ==
             options.name_collapse_exemptions.end()) {
diff --git a/tools/aapt2/java/JavaClassGenerator.cpp b/tools/aapt2/java/JavaClassGenerator.cpp
index a963d98..a25ca22 100644
--- a/tools/aapt2/java/JavaClassGenerator.cpp
+++ b/tools/aapt2/java/JavaClassGenerator.cpp
@@ -548,10 +548,11 @@
     }
 
     // We need to make sure we hide the fact that we are generating kAttrPrivate attributes.
-    const ResourceNameRef resource_name(
-        package_name_to_generate,
-        type.type == ResourceType::kAttrPrivate ? ResourceType::kAttr : type.type,
-        unmangled_name.value());
+    const auto target_type = type.named_type.type == ResourceType::kAttrPrivate
+                                 ? ResourceNamedTypeWithDefaultName(ResourceType::kAttr)
+                                 : type.named_type;
+    const ResourceNameRef resource_name(package_name_to_generate, target_type,
+                                        unmangled_name.value());
 
     // Check to see if the unmangled name is a valid Java name (not a keyword).
     if (!IsValidSymbol(unmangled_name.value())) {
@@ -616,7 +617,8 @@
 
   for (const auto& package : table_->packages) {
     for (const auto& type : package->types) {
-      if (type->type == ResourceType::kAttrPrivate || type->type == ResourceType::kMacro) {
+      if (type->named_type.type == ResourceType::kAttrPrivate ||
+          type->named_type.type == ResourceType::kMacro) {
         // We generate kAttrPrivate as part of the kAttr type, so skip them here.
         // Macros are not actual resources, so skip them as well.
         continue;
@@ -628,7 +630,7 @@
       std::unique_ptr<ClassDefinition> class_def;
       if (out != nullptr) {
         class_def = util::make_unique<ClassDefinition>(
-            to_string(type->type), ClassQualifier::kStatic, force_creation_if_empty);
+            to_string(type->named_type.type), ClassQualifier::kStatic, force_creation_if_empty);
       }
 
       if (!ProcessType(package_name_to_generate, *package, *type, class_def.get(),
@@ -636,9 +638,10 @@
         return false;
       }
 
-      if (type->type == ResourceType::kAttr) {
+      if (type->named_type.type == ResourceType::kAttr) {
         // Also include private attributes in this same class.
-        if (const ResourceTableType* priv_type = package->FindType(ResourceType::kAttrPrivate)) {
+        if (const ResourceTableType* priv_type =
+                package->FindTypeWithDefaultName(ResourceType::kAttrPrivate)) {
           if (!ProcessType(package_name_to_generate, *package, *priv_type, class_def.get(),
                            rewrite_method.get(), r_txt_printer.get())) {
             return false;
@@ -646,7 +649,7 @@
         }
       }
 
-      if (out != nullptr && type->type == ResourceType::kStyleable && is_public) {
+      if (out != nullptr && type->named_type.type == ResourceType::kStyleable && is_public) {
         // When generating a public R class, we don't want Styleable to be part
         // of the API. It is only emitted for documentation purposes.
         class_def->GetCommentBuilder()->AppendComment("@doconly");
diff --git a/tools/aapt2/java/ProguardRules.cpp b/tools/aapt2/java/ProguardRules.cpp
index e53e220..80a46d5 100644
--- a/tools/aapt2/java/ProguardRules.cpp
+++ b/tools/aapt2/java/ProguardRules.cpp
@@ -517,7 +517,7 @@
     for (auto& type : pkg->types) {
       for (auto& entry : type->entries) {
         for (auto& config_value : entry->values) {
-          ResourceName from(pkg->name, type->type, entry->name);
+          ResourceName from(pkg->name, type->named_type, entry->name);
           ReferenceVisitor visitor(context, from, keep_set);
           config_value->value->Accept(&visitor);
         }
diff --git a/tools/aapt2/link/AutoVersioner.cpp b/tools/aapt2/link/AutoVersioner.cpp
index 328ac970..3dbd7e6 100644
--- a/tools/aapt2/link/AutoVersioner.cpp
+++ b/tools/aapt2/link/AutoVersioner.cpp
@@ -75,7 +75,7 @@
   CloningValueTransformer cloner(&table->string_pool);
   for (auto& package : table->packages) {
     for (auto& type : package->types) {
-      if (type->type != ResourceType::kStyle) {
+      if (type->named_type.type != ResourceType::kStyle) {
         continue;
       }
 
diff --git a/tools/aapt2/link/NoDefaultResourceRemover.cpp b/tools/aapt2/link/NoDefaultResourceRemover.cpp
index 05990de..ab3c04e5 100644
--- a/tools/aapt2/link/NoDefaultResourceRemover.cpp
+++ b/tools/aapt2/link/NoDefaultResourceRemover.cpp
@@ -76,7 +76,7 @@
       });
 
       for (auto iter = remove_iter; iter != end_iter; ++iter) {
-        const ResourceName name(pkg->name, type->type, (*iter)->name);
+        const ResourceName name(pkg->name, type->named_type, (*iter)->name);
         IDiagnostics* diag = context->GetDiagnostics();
         diag->Warn(DiagMessage() << "removing resource " << name
                                  << " without required default value");
diff --git a/tools/aapt2/link/PrivateAttributeMover.cpp b/tools/aapt2/link/PrivateAttributeMover.cpp
index 675b02a..8c6c743 100644
--- a/tools/aapt2/link/PrivateAttributeMover.cpp
+++ b/tools/aapt2/link/PrivateAttributeMover.cpp
@@ -57,7 +57,7 @@
 
 bool PrivateAttributeMover::Consume(IAaptContext* context, ResourceTable* table) {
   for (auto& package : table->packages) {
-    ResourceTableType* type = package->FindType(ResourceType::kAttr);
+    ResourceTableType* type = package->FindTypeWithDefaultName(ResourceType::kAttr);
     if (!type) {
       continue;
     }
@@ -80,7 +80,8 @@
       continue;
     }
 
-    ResourceTableType* priv_attr_type = package->FindOrCreateType(ResourceType::kAttrPrivate);
+    auto attr_private_type = ResourceNamedTypeWithDefaultName(ResourceType::kAttrPrivate);
+    ResourceTableType* priv_attr_type = package->FindOrCreateType(attr_private_type);
     CHECK(priv_attr_type->entries.empty());
     priv_attr_type->entries = std::move(private_attr_entries);
   }
diff --git a/tools/aapt2/link/PrivateAttributeMover_test.cpp b/tools/aapt2/link/PrivateAttributeMover_test.cpp
index 168234b..32335b7 100644
--- a/tools/aapt2/link/PrivateAttributeMover_test.cpp
+++ b/tools/aapt2/link/PrivateAttributeMover_test.cpp
@@ -41,13 +41,13 @@
   ResourceTablePackage* package = table->FindPackage("android");
   ASSERT_NE(package, nullptr);
 
-  ResourceTableType* type = package->FindType(ResourceType::kAttr);
+  ResourceTableType* type = package->FindTypeWithDefaultName(ResourceType::kAttr);
   ASSERT_NE(type, nullptr);
   ASSERT_EQ(type->entries.size(), 2u);
   EXPECT_NE(type->FindEntry("publicA"), nullptr);
   EXPECT_NE(type->FindEntry("publicB"), nullptr);
 
-  type = package->FindType(ResourceType::kAttrPrivate);
+  type = package->FindTypeWithDefaultName(ResourceType::kAttrPrivate);
   ASSERT_NE(type, nullptr);
   ASSERT_EQ(type->entries.size(), 2u);
   EXPECT_NE(type->FindEntry("privateA"), nullptr);
@@ -68,11 +68,11 @@
   ResourceTablePackage* package = table->FindPackage("android");
   ASSERT_NE(package, nullptr);
 
-  ResourceTableType* type = package->FindType(ResourceType::kAttr);
+  ResourceTableType* type = package->FindTypeWithDefaultName(ResourceType::kAttr);
   ASSERT_NE(type, nullptr);
   ASSERT_EQ(type->entries.size(), 2u);
 
-  type = package->FindType(ResourceType::kAttrPrivate);
+  type = package->FindTypeWithDefaultName(ResourceType::kAttrPrivate);
   ASSERT_EQ(type, nullptr);
 }
 
@@ -87,12 +87,12 @@
   ResourceTablePackage* package = table->FindPackage("android");
   ASSERT_NE(nullptr, package);
 
-  ASSERT_EQ(nullptr, package->FindType(ResourceType::kAttrPrivate));
+  ASSERT_EQ(nullptr, package->FindTypeWithDefaultName(ResourceType::kAttrPrivate));
 
   PrivateAttributeMover mover;
   ASSERT_TRUE(mover.Consume(context.get(), table.get()));
 
-  ASSERT_EQ(nullptr, package->FindType(ResourceType::kAttrPrivate));
+  ASSERT_EQ(nullptr, package->FindTypeWithDefaultName(ResourceType::kAttrPrivate));
 }
 
 }  // namespace aapt
diff --git a/tools/aapt2/link/ProductFilter.cpp b/tools/aapt2/link/ProductFilter.cpp
index 793740a..0c54a73 100644
--- a/tools/aapt2/link/ProductFilter.cpp
+++ b/tools/aapt2/link/ProductFilter.cpp
@@ -98,7 +98,7 @@
             // End of the array, or we saw a different config,
             // so this must be the end of a range of products.
             // Select the product to keep from the set of products defined.
-            ResourceNameRef name(pkg->name, type->type, entry->name);
+            ResourceNameRef name(pkg->name, type->named_type, entry->name);
             auto value_to_keep = SelectProductToKeep(
                 name, start_range_iter, iter, context->GetDiagnostics());
             if (value_to_keep == iter) {
diff --git a/tools/aapt2/link/ReferenceLinker.cpp b/tools/aapt2/link/ReferenceLinker.cpp
index 5372cf2..d1fbffa 100644
--- a/tools/aapt2/link/ReferenceLinker.cpp
+++ b/tools/aapt2/link/ReferenceLinker.cpp
@@ -468,7 +468,7 @@
     for (auto& type : package->types) {
       for (auto& entry : type->entries) {
         // First, unmangle the name if necessary.
-        ResourceName name(package->name, type->type, entry->name);
+        ResourceName name(package->name, type->named_type, entry->name);
         NameMangler::Unmangle(&name.entry, &name.package);
 
         // Symbol state information may be lost if there is no value for the resource.
diff --git a/tools/aapt2/link/TableMerger.cpp b/tools/aapt2/link/TableMerger.cpp
index d78f0ac..caaaba6 100644
--- a/tools/aapt2/link/TableMerger.cpp
+++ b/tools/aapt2/link/TableMerger.cpp
@@ -235,7 +235,7 @@
   bool error = false;
 
   for (auto& src_type : src_package->types) {
-    ResourceTableType* dst_type = main_package_->FindOrCreateType(src_type->type);
+    ResourceTableType* dst_type = main_package_->FindOrCreateType(src_type->named_type);
     if (!MergeType(context_, src, dst_type, src_type.get())) {
       error = true;
       continue;
@@ -254,7 +254,7 @@
         dst_entry = dst_type->FindEntry(entry_name);
       }
 
-      const ResourceNameRef res_name(src_package->name, src_type->type, src_entry->name);
+      const ResourceNameRef res_name(src_package->name, src_type->named_type, src_entry->name);
 
       if (!dst_entry) {
         context_->GetDiagnostics()->Error(DiagMessage(src)
@@ -349,7 +349,7 @@
   file_ref->file = file;
 
   ResourceTablePackage* pkg = table.FindOrCreatePackage(file_desc.name.package);
-  pkg->FindOrCreateType(file_desc.name.type.type)
+  pkg->FindOrCreateType(file_desc.name.type)
       ->FindOrCreateEntry(file_desc.name.entry)
       ->FindOrCreateValue(file_desc.config, {})
       ->value = std::move(file_ref);
diff --git a/tools/aapt2/optimize/ResourceFilter.cpp b/tools/aapt2/optimize/ResourceFilter.cpp
index 08c045b..db84b66 100644
--- a/tools/aapt2/optimize/ResourceFilter.cpp
+++ b/tools/aapt2/optimize/ResourceFilter.cpp
@@ -28,7 +28,7 @@
   for (auto& package : table->packages) {
     for (auto& type : package->types) {
       for (auto it = type->entries.begin(); it != type->entries.end(); ) {
-        ResourceName resource = ResourceName({}, type->type, (*it)->name);
+        ResourceName resource = ResourceName({}, type->named_type, (*it)->name);
         if (exclude_list_.find(resource) != exclude_list_.end()) {
           it = type->entries.erase(it);
         } else {
diff --git a/tools/aapt2/split/TableSplitter.cpp b/tools/aapt2/split/TableSplitter.cpp
index 116b2ab9..85d150f 100644
--- a/tools/aapt2/split/TableSplitter.cpp
+++ b/tools/aapt2/split/TableSplitter.cpp
@@ -189,7 +189,7 @@
     }
 
     for (auto& type : pkg->types) {
-      if (type->type == ResourceType::kMipmap) {
+      if (type->named_type.type == ResourceType::kMipmap) {
         // Always keep mipmaps.
         continue;
       }
@@ -241,7 +241,7 @@
             // Create the same resource structure in the split. We do this lazily because we might
             // not have actual values for each type/entry.
             ResourceTablePackage* split_pkg = split_table->FindPackage(pkg->name);
-            ResourceTableType* split_type = split_pkg->FindOrCreateType(type->type);
+            ResourceTableType* split_type = split_pkg->FindOrCreateType(type->named_type);
             split_type->visibility_level = type->visibility_level;
 
             ResourceEntry* split_entry = split_type->FindOrCreateEntry(entry->name);