mirror of
https://github.com/carbon-language/carbon-lang.git
synced 2026-09-24 21:10:12 +01:00
Move type functions off Context (#4951)
This creates a new check/type.h for most logic, and also moves some functions to TypeStore in sem_ir/type.h. My approach for TypeStore is to focus on moving the read-only functions there.
This commit is contained in:
@@ -42,6 +42,7 @@ cc_library(
|
||||
"return.cpp",
|
||||
"subpattern.cpp",
|
||||
"subst.cpp",
|
||||
"type.cpp",
|
||||
"type_completion.cpp",
|
||||
],
|
||||
hdrs = [
|
||||
@@ -78,6 +79,7 @@ cc_library(
|
||||
"return.h",
|
||||
"subpattern.h",
|
||||
"subst.h",
|
||||
"type.h",
|
||||
"type_completion.h",
|
||||
],
|
||||
deps = [
|
||||
|
||||
@@ -9,6 +9,7 @@
|
||||
#include "toolchain/check/convert.h"
|
||||
#include "toolchain/check/deduce.h"
|
||||
#include "toolchain/check/function.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/diagnostics/format_providers.h"
|
||||
#include "toolchain/sem_ir/builtin_function_kind.h"
|
||||
#include "toolchain/sem_ir/entity_with_params_base.h"
|
||||
@@ -118,8 +119,9 @@ static auto PerformCallToGenericInterface(
|
||||
if (!callee_specific_id) {
|
||||
return SemIR::ErrorInst::SingletonInstId;
|
||||
}
|
||||
return context.GetOrAddInst(loc_id, context.FacetTypeFromInterface(
|
||||
interface_id, *callee_specific_id));
|
||||
return context.GetOrAddInst(
|
||||
loc_id,
|
||||
FacetTypeFromInterface(context, interface_id, *callee_specific_id));
|
||||
}
|
||||
|
||||
auto PerformCall(Context& context, SemIR::LocId loc_id, SemIR::InstId callee_id,
|
||||
@@ -164,8 +166,8 @@ auto PerformCall(Context& context, SemIR::LocId loc_id, SemIR::InstId callee_id,
|
||||
callee_id = context.GetOrAddInst(
|
||||
context.insts().GetLocId(callee_id),
|
||||
SemIR::SpecificFunction{
|
||||
.type_id = context.GetSingletonType(
|
||||
SemIR::SpecificFunctionType::SingletonInstId),
|
||||
.type_id = GetSingletonType(
|
||||
context, SemIR::SpecificFunctionType::SingletonInstId),
|
||||
.callee_id = callee_id,
|
||||
.specific_id = *callee_specific_id});
|
||||
if (callee_function.self_type_id.has_value()) {
|
||||
@@ -201,7 +203,7 @@ auto PerformCall(Context& context, SemIR::LocId loc_id, SemIR::InstId callee_id,
|
||||
// For functions with an implicit return type, the return type is the
|
||||
// empty tuple type.
|
||||
if (!return_info.type_id.has_value()) {
|
||||
return_info.type_id = context.GetTupleType({});
|
||||
return_info.type_id = GetTupleType(context, {});
|
||||
}
|
||||
break;
|
||||
case SemIR::InitRepr::ByCopy:
|
||||
|
||||
@@ -18,6 +18,7 @@
|
||||
#include "toolchain/check/import_cpp.h"
|
||||
#include "toolchain/check/import_ref.h"
|
||||
#include "toolchain/check/node_id_traversal.h"
|
||||
#include "toolchain/check/type.h"
|
||||
|
||||
namespace Carbon::Check {
|
||||
|
||||
@@ -92,7 +93,7 @@ auto CheckUnit::Run() -> void {
|
||||
auto CheckUnit::InitPackageScopeAndImports() -> void {
|
||||
// Importing makes many namespaces, so only canonicalize the type once.
|
||||
auto namespace_type_id =
|
||||
context_.GetSingletonType(SemIR::NamespaceType::SingletonInstId);
|
||||
GetSingletonType(context_, SemIR::NamespaceType::SingletonInstId);
|
||||
|
||||
// Define the package scope, with an instruction for `package` expressions to
|
||||
// reference.
|
||||
|
||||
@@ -227,123 +227,6 @@ auto Context::Finalize() -> void {
|
||||
global_init_.Finalize();
|
||||
}
|
||||
|
||||
auto Context::GetTypeIdForTypeConstant(SemIR::ConstantId constant_id)
|
||||
-> SemIR::TypeId {
|
||||
CARBON_CHECK(constant_id.is_constant(),
|
||||
"Canonicalizing non-constant type: {0}", constant_id);
|
||||
auto type_id =
|
||||
insts().Get(constant_values().GetInstId(constant_id)).type_id();
|
||||
CARBON_CHECK(type_id == SemIR::TypeType::SingletonTypeId ||
|
||||
constant_id == SemIR::ErrorInst::SingletonConstantId,
|
||||
"Forming type ID for non-type constant of type {0}",
|
||||
types().GetAsInst(type_id));
|
||||
|
||||
return SemIR::TypeId::ForTypeConstant(constant_id);
|
||||
}
|
||||
|
||||
auto Context::FacetTypeFromInterface(SemIR::InterfaceId interface_id,
|
||||
SemIR::SpecificId specific_id)
|
||||
-> SemIR::FacetType {
|
||||
SemIR::FacetTypeId facet_type_id = facet_types().Add(
|
||||
SemIR::FacetTypeInfo{.impls_constraints = {{interface_id, specific_id}},
|
||||
.other_requirements = false});
|
||||
return {.type_id = SemIR::TypeType::SingletonTypeId,
|
||||
.facet_type_id = facet_type_id};
|
||||
}
|
||||
|
||||
// Gets or forms a type_id for a type, given the instruction kind and arguments.
|
||||
template <typename InstT, typename... EachArgT>
|
||||
static auto GetTypeImpl(Context& context, EachArgT... each_arg)
|
||||
-> SemIR::TypeId {
|
||||
// TODO: Remove inst_id parameter from TryEvalInst.
|
||||
InstT inst = {SemIR::TypeType::SingletonTypeId, each_arg...};
|
||||
return context.GetTypeIdForTypeConstant(
|
||||
TryEvalInst(context, SemIR::InstId::None, inst));
|
||||
}
|
||||
|
||||
// Gets or forms a type_id for a type, given the instruction kind and arguments,
|
||||
// and completes the type. This should only be used when type completion cannot
|
||||
// fail.
|
||||
template <typename InstT, typename... EachArgT>
|
||||
static auto GetCompleteTypeImpl(Context& context, EachArgT... each_arg)
|
||||
-> SemIR::TypeId {
|
||||
auto type_id = GetTypeImpl<InstT>(context, each_arg...);
|
||||
CompleteTypeOrCheckFail(context, type_id);
|
||||
return type_id;
|
||||
}
|
||||
|
||||
auto Context::GetStructType(SemIR::StructTypeFieldsId fields_id)
|
||||
-> SemIR::TypeId {
|
||||
return GetTypeImpl<SemIR::StructType>(*this, fields_id);
|
||||
}
|
||||
|
||||
auto Context::GetTupleType(llvm::ArrayRef<SemIR::TypeId> type_ids)
|
||||
-> SemIR::TypeId {
|
||||
return GetTypeImpl<SemIR::TupleType>(*this,
|
||||
type_blocks().AddCanonical(type_ids));
|
||||
}
|
||||
|
||||
auto Context::GetAssociatedEntityType(SemIR::TypeId interface_type_id)
|
||||
-> SemIR::TypeId {
|
||||
return GetTypeImpl<SemIR::AssociatedEntityType>(*this, interface_type_id);
|
||||
}
|
||||
|
||||
auto Context::GetSingletonType(SemIR::InstId singleton_id) -> SemIR::TypeId {
|
||||
CARBON_CHECK(SemIR::IsSingletonInstId(singleton_id));
|
||||
auto type_id = GetTypeIdForTypeInst(singleton_id);
|
||||
// To keep client code simpler, complete builtin types before returning them.
|
||||
CompleteTypeOrCheckFail(*this, type_id);
|
||||
return type_id;
|
||||
}
|
||||
|
||||
auto Context::GetClassType(SemIR::ClassId class_id,
|
||||
SemIR::SpecificId specific_id) -> SemIR::TypeId {
|
||||
return GetTypeImpl<SemIR::ClassType>(*this, class_id, specific_id);
|
||||
}
|
||||
|
||||
auto Context::GetFunctionType(SemIR::FunctionId fn_id,
|
||||
SemIR::SpecificId specific_id) -> SemIR::TypeId {
|
||||
return GetCompleteTypeImpl<SemIR::FunctionType>(*this, fn_id, specific_id);
|
||||
}
|
||||
|
||||
auto Context::GetFunctionTypeWithSelfType(
|
||||
SemIR::InstId interface_function_type_id, SemIR::InstId self_id)
|
||||
-> SemIR::TypeId {
|
||||
return GetCompleteTypeImpl<SemIR::FunctionTypeWithSelfType>(
|
||||
*this, interface_function_type_id, self_id);
|
||||
}
|
||||
|
||||
auto Context::GetGenericClassType(SemIR::ClassId class_id,
|
||||
SemIR::SpecificId enclosing_specific_id)
|
||||
-> SemIR::TypeId {
|
||||
return GetCompleteTypeImpl<SemIR::GenericClassType>(*this, class_id,
|
||||
enclosing_specific_id);
|
||||
}
|
||||
|
||||
auto Context::GetGenericInterfaceType(SemIR::InterfaceId interface_id,
|
||||
SemIR::SpecificId enclosing_specific_id)
|
||||
-> SemIR::TypeId {
|
||||
return GetCompleteTypeImpl<SemIR::GenericInterfaceType>(
|
||||
*this, interface_id, enclosing_specific_id);
|
||||
}
|
||||
|
||||
auto Context::GetInterfaceType(SemIR::InterfaceId interface_id,
|
||||
SemIR::SpecificId specific_id) -> SemIR::TypeId {
|
||||
return GetTypeImpl<SemIR::FacetType>(
|
||||
*this, FacetTypeFromInterface(interface_id, specific_id).facet_type_id);
|
||||
}
|
||||
|
||||
auto Context::GetPointerType(SemIR::TypeId pointee_type_id) -> SemIR::TypeId {
|
||||
return GetTypeImpl<SemIR::PointerType>(*this, pointee_type_id);
|
||||
}
|
||||
|
||||
auto Context::GetUnboundElementType(SemIR::TypeId class_type_id,
|
||||
SemIR::TypeId element_type_id)
|
||||
-> SemIR::TypeId {
|
||||
return GetTypeImpl<SemIR::UnboundElementType>(*this, class_type_id,
|
||||
element_type_id);
|
||||
}
|
||||
|
||||
auto Context::PrintForStackDump(llvm::raw_ostream& output) const -> void {
|
||||
output << "Check::Context\n";
|
||||
|
||||
|
||||
@@ -178,97 +178,6 @@ class Context {
|
||||
sem_ir().insts().SetLocId(inst_id, SemIR::LocId(node_id));
|
||||
}
|
||||
|
||||
// Returns the type ID for a constant that is a type value, i.e. it is a value
|
||||
// of type `TypeType`.
|
||||
//
|
||||
// Facet values are of the same typishness as types, but are not themselves
|
||||
// types, so they can not be passed here. They should be converted to a type
|
||||
// through an `as type` conversion, that is, to a value of type `TypeType`.
|
||||
auto GetTypeIdForTypeConstant(SemIR::ConstantId constant_id) -> SemIR::TypeId;
|
||||
|
||||
// Returns the type ID for an instruction whose constant value is a type
|
||||
// value, i.e. it is a value of type `TypeType`.
|
||||
//
|
||||
// Instructions whose values are facet values (see `FacetValue`) produce a
|
||||
// value of the same typishness as types, but which are themselves not types,
|
||||
// so they can not be passed here. They should be converted to a type through
|
||||
// an `as type` conversion, such as to a `FacetAccessType` instruction whose
|
||||
// value is of type `TypeType`.
|
||||
auto GetTypeIdForTypeInst(SemIR::InstId inst_id) -> SemIR::TypeId {
|
||||
return GetTypeIdForTypeConstant(constant_values().Get(inst_id));
|
||||
}
|
||||
|
||||
// Returns whether `type_id` represents a facet type.
|
||||
auto IsFacetType(SemIR::TypeId type_id) -> bool {
|
||||
return type_id == SemIR::TypeType::SingletonTypeId ||
|
||||
types().Is<SemIR::FacetType>(type_id);
|
||||
}
|
||||
|
||||
// Create a FacetType typed instruction object consisting of a single
|
||||
// interface.
|
||||
auto FacetTypeFromInterface(SemIR::InterfaceId interface_id,
|
||||
SemIR::SpecificId specific_id)
|
||||
-> SemIR::FacetType;
|
||||
|
||||
// TODO: Consider moving these `Get*Type` functions to a separate class.
|
||||
|
||||
// Gets the type to use for an unbound associated entity declared in this
|
||||
// interface. For example, this is the type of `I.T` after
|
||||
// `interface I { let T:! type; }`.
|
||||
// The name of the interface is used for diagnostics.
|
||||
// TODO: Should we use a different type for each such entity, or the same type
|
||||
// for all associated entities?
|
||||
auto GetAssociatedEntityType(SemIR::TypeId interface_type_id)
|
||||
-> SemIR::TypeId;
|
||||
|
||||
// Gets a singleton type. The returned type will be complete. Requires that
|
||||
// `singleton_id` is already validated to be a singleton.
|
||||
auto GetSingletonType(SemIR::InstId singleton_id) -> SemIR::TypeId;
|
||||
|
||||
// Gets a class type.
|
||||
auto GetClassType(SemIR::ClassId class_id, SemIR::SpecificId specific_id)
|
||||
-> SemIR::TypeId;
|
||||
|
||||
// Gets a function type. The returned type will be complete.
|
||||
auto GetFunctionType(SemIR::FunctionId fn_id, SemIR::SpecificId specific_id)
|
||||
-> SemIR::TypeId;
|
||||
|
||||
// Gets the type of an associated function with the `Self` parameter bound to
|
||||
// a particular value. The returned type will be complete.
|
||||
auto GetFunctionTypeWithSelfType(SemIR::InstId interface_function_type_id,
|
||||
SemIR::InstId self_id) -> SemIR::TypeId;
|
||||
|
||||
// Gets a generic class type, which is the type of a name of a generic class,
|
||||
// such as the type of `Vector` given `class Vector(T:! type)`. The returned
|
||||
// type will be complete.
|
||||
auto GetGenericClassType(SemIR::ClassId class_id,
|
||||
SemIR::SpecificId enclosing_specific_id)
|
||||
-> SemIR::TypeId;
|
||||
|
||||
// Gets a generic interface type, which is the type of a name of a generic
|
||||
// interface, such as the type of `AddWith` given
|
||||
// `interface AddWith(T:! type)`. The returned type will be complete.
|
||||
auto GetGenericInterfaceType(SemIR::InterfaceId interface_id,
|
||||
SemIR::SpecificId enclosing_specific_id)
|
||||
-> SemIR::TypeId;
|
||||
|
||||
// Gets the facet type corresponding to a particular interface.
|
||||
auto GetInterfaceType(SemIR::InterfaceId interface_id,
|
||||
SemIR::SpecificId specific_id) -> SemIR::TypeId;
|
||||
|
||||
// Returns a pointer type whose pointee type is `pointee_type_id`.
|
||||
auto GetPointerType(SemIR::TypeId pointee_type_id) -> SemIR::TypeId;
|
||||
|
||||
// Returns a struct type with the given fields.
|
||||
auto GetStructType(SemIR::StructTypeFieldsId fields_id) -> SemIR::TypeId;
|
||||
|
||||
// Returns a tuple type with the given element types.
|
||||
auto GetTupleType(llvm::ArrayRef<SemIR::TypeId> type_ids) -> SemIR::TypeId;
|
||||
|
||||
// Returns an unbound element type.
|
||||
auto GetUnboundElementType(SemIR::TypeId class_type_id,
|
||||
SemIR::TypeId element_type_id) -> SemIR::TypeId;
|
||||
|
||||
// Adds an exported name.
|
||||
auto AddExport(SemIR::InstId inst_id) -> void { exports_.push_back(inst_id); }
|
||||
|
||||
|
||||
@@ -16,6 +16,7 @@
|
||||
#include "toolchain/check/impl_lookup.h"
|
||||
#include "toolchain/check/operator.h"
|
||||
#include "toolchain/check/pattern_match.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/check/type_completion.h"
|
||||
#include "toolchain/diagnostics/format_providers.h"
|
||||
#include "toolchain/sem_ir/copy_on_write_block.h"
|
||||
@@ -159,8 +160,8 @@ static auto MakeElementAccessInst(Context& context, SemIR::LocId loc_id,
|
||||
// index so that we don't need an integer literal instruction here, and
|
||||
// remove this special case.
|
||||
auto index_id = block.template AddInst<SemIR::IntValue>(
|
||||
loc_id, {.type_id = context.GetSingletonType(
|
||||
SemIR::IntLiteralType::SingletonInstId),
|
||||
loc_id, {.type_id = GetSingletonType(
|
||||
context, SemIR::IntLiteralType::SingletonInstId),
|
||||
.int_id = context.ints().Add(static_cast<int64_t>(i))});
|
||||
return block.template AddInst<AccessInstT>(
|
||||
loc_id, {elem_type_id, aggregate_id, index_id});
|
||||
@@ -964,7 +965,7 @@ static auto PerformBuiltinConversion(Context& context, SemIR::LocId loc_id,
|
||||
// iterative approach.
|
||||
type_ids.push_back(ExprAsType(context, loc_id, tuple_inst_id).type_id);
|
||||
}
|
||||
auto tuple_type_id = context.GetTupleType(type_ids);
|
||||
auto tuple_type_id = GetTupleType(context, type_ids);
|
||||
return sem_ir.types().GetInstId(tuple_type_id);
|
||||
}
|
||||
|
||||
@@ -1298,7 +1299,7 @@ auto ConvertToBoolValue(Context& context, SemIR::LocId loc_id,
|
||||
SemIR::InstId value_id) -> SemIR::InstId {
|
||||
return ConvertToValueOfType(
|
||||
context, loc_id, value_id,
|
||||
context.GetSingletonType(SemIR::BoolType::SingletonInstId));
|
||||
GetSingletonType(context, SemIR::BoolType::SingletonInstId));
|
||||
}
|
||||
|
||||
auto ConvertForExplicitAs(Context& context, Parse::NodeId as_node,
|
||||
@@ -1361,7 +1362,7 @@ auto ExprAsType(Context& context, SemIR::LocId loc_id, SemIR::InstId value_id)
|
||||
}
|
||||
|
||||
return {.inst_id = type_inst_id,
|
||||
.type_id = context.GetTypeIdForTypeConstant(type_const_id)};
|
||||
.type_id = context.types().GetTypeIdForTypeConstantId(type_const_id)};
|
||||
}
|
||||
|
||||
} // namespace Carbon::Check
|
||||
|
||||
@@ -551,7 +551,8 @@ auto DeductionContext::CheckDeductionIsComplete() -> bool {
|
||||
auto param_type_const_id = SubstConstant(
|
||||
context(), binding_type_id.AsConstantId(), substitutions_);
|
||||
CARBON_CHECK(param_type_const_id.has_value());
|
||||
binding_type_id = context().GetTypeIdForTypeConstant(param_type_const_id);
|
||||
binding_type_id =
|
||||
context().types().GetTypeIdForTypeConstantId(param_type_const_id);
|
||||
|
||||
// TODO: Suppress diagnostics here if `diagnose_` is false.
|
||||
DiagnosticAnnotationScope annotate_diagnostics(
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
#include "toolchain/check/diagnostic_helpers.h"
|
||||
#include "toolchain/check/generic.h"
|
||||
#include "toolchain/check/import_ref.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/check/type_completion.h"
|
||||
#include "toolchain/diagnostics/diagnostic_emitter.h"
|
||||
#include "toolchain/diagnostics/format_providers.h"
|
||||
@@ -124,7 +125,7 @@ class EvalContext {
|
||||
|
||||
// Gets the constant value of the specified type in this context.
|
||||
auto GetConstantValueAsType(SemIR::TypeId id) -> SemIR::TypeId {
|
||||
return context().GetTypeIdForTypeConstant(GetConstantValue(id));
|
||||
return context().types().GetTypeIdForTypeConstantId(GetConstantValue(id));
|
||||
}
|
||||
|
||||
// Gets the instruction describing the constant value of the specified type in
|
||||
@@ -332,7 +333,7 @@ static auto GetConstantValue(EvalContext& eval_context, SemIR::TypeId type_id,
|
||||
Phase* phase) -> SemIR::TypeId {
|
||||
auto const_id = eval_context.GetConstantValue(type_id);
|
||||
*phase = LatestPhase(*phase, GetPhase(eval_context, const_id));
|
||||
return eval_context.context().GetTypeIdForTypeConstant(const_id);
|
||||
return eval_context.context().types().GetTypeIdForTypeConstantId(const_id);
|
||||
}
|
||||
|
||||
// If the given instruction block contains only constants, returns a
|
||||
@@ -689,7 +690,7 @@ static auto MakeIntTypeResult(Context& context, SemIRLoc loc,
|
||||
SemIR::IntKind int_kind, SemIR::InstId width_id,
|
||||
Phase phase) -> SemIR::ConstantId {
|
||||
auto result = SemIR::IntType{
|
||||
.type_id = context.GetSingletonType(SemIR::TypeType::SingletonInstId),
|
||||
.type_id = GetSingletonType(context, SemIR::TypeType::SingletonInstId),
|
||||
.int_kind = int_kind,
|
||||
.bit_width_id = width_id};
|
||||
if (!ValidateIntType(context, loc, result)) {
|
||||
@@ -1751,8 +1752,9 @@ static auto TryEvalInstInContext(EvalContext& eval_context,
|
||||
// A non-generic interface declaration evaluates to a facet type.
|
||||
return MakeConstantResult(
|
||||
eval_context.context(),
|
||||
eval_context.context().FacetTypeFromInterface(
|
||||
interface_decl.interface_id, SemIR::SpecificId::None),
|
||||
FacetTypeFromInterface(eval_context.context(),
|
||||
interface_decl.interface_id,
|
||||
SemIR::SpecificId::None),
|
||||
Phase::Concrete);
|
||||
}
|
||||
|
||||
@@ -2074,8 +2076,8 @@ static auto TryEvalInstInContext(EvalContext& eval_context,
|
||||
|
||||
case CARBON_KIND(SemIR::RequireCompleteType require_complete): {
|
||||
auto phase = Phase::Concrete;
|
||||
auto witness_type_id = eval_context.context().GetSingletonType(
|
||||
SemIR::WitnessType::SingletonInstId);
|
||||
auto witness_type_id = GetSingletonType(
|
||||
eval_context.context(), SemIR::WitnessType::SingletonInstId);
|
||||
auto complete_type_id = GetConstantValue(
|
||||
eval_context, require_complete.complete_type_id, &phase);
|
||||
|
||||
|
||||
+11
-10
@@ -9,6 +9,7 @@
|
||||
#include "toolchain/check/eval.h"
|
||||
#include "toolchain/check/generic_region_stack.h"
|
||||
#include "toolchain/check/subst.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/check/type_completion.h"
|
||||
#include "toolchain/sem_ir/generic.h"
|
||||
#include "toolchain/sem_ir/ids.h"
|
||||
@@ -179,7 +180,7 @@ static auto AddGenericTypeToEvalBlock(
|
||||
SubstInst(context, context.types().GetInstId(type_id),
|
||||
RebuildGenericConstantInEvalBlockCallbacks(
|
||||
context, generic_id, region, loc_id, constants_in_generic));
|
||||
return context.GetTypeIdForTypeInst(type_inst_id);
|
||||
return context.types().GetTypeIdForTypeInstId(type_inst_id);
|
||||
}
|
||||
|
||||
// Adds instructions to compute the substituted value of `inst_id` in each
|
||||
@@ -500,20 +501,20 @@ auto GetInstForSpecific(Context& context, SemIR::SpecificId specific_id)
|
||||
CARBON_KIND_SWITCH(decl) {
|
||||
case CARBON_KIND(SemIR::ClassDecl class_decl): {
|
||||
return context.types().GetInstId(
|
||||
context.GetClassType(class_decl.class_id, specific_id));
|
||||
GetClassType(context, class_decl.class_id, specific_id));
|
||||
}
|
||||
case CARBON_KIND(SemIR::InterfaceDecl interface_decl): {
|
||||
return context.types().GetInstId(
|
||||
context.GetInterfaceType(interface_decl.interface_id, specific_id));
|
||||
GetInterfaceType(context, interface_decl.interface_id, specific_id));
|
||||
}
|
||||
case SemIR::FunctionDecl::Kind: {
|
||||
return context.constant_values().GetInstId(
|
||||
TryEvalInst(context, SemIR::InstId::None,
|
||||
SemIR::SpecificFunction{
|
||||
.type_id = context.GetSingletonType(
|
||||
SemIR::SpecificFunctionType::SingletonInstId),
|
||||
.callee_id = generic.decl_id,
|
||||
.specific_id = specific_id}));
|
||||
return context.constant_values().GetInstId(TryEvalInst(
|
||||
context, SemIR::InstId::None,
|
||||
SemIR::SpecificFunction{
|
||||
.type_id = GetSingletonType(
|
||||
context, SemIR::SpecificFunctionType::SingletonInstId),
|
||||
.callee_id = generic.decl_id,
|
||||
.specific_id = specific_id}));
|
||||
}
|
||||
case SemIR::AssociatedConstantDecl::Kind: {
|
||||
// TODO: We don't have a good instruction to use here.
|
||||
|
||||
@@ -5,6 +5,7 @@
|
||||
#include "toolchain/check/context.h"
|
||||
#include "toolchain/check/convert.h"
|
||||
#include "toolchain/check/handle.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/parse/node_kind.h"
|
||||
|
||||
namespace Carbon::Check {
|
||||
@@ -51,7 +52,7 @@ auto HandleParseNode(Context& context, Parse::ArrayExprId node_id) -> bool {
|
||||
|
||||
bound_inst_id = ConvertToValueOfType(
|
||||
context, context.insts().GetLocId(bound_inst_id), bound_inst_id,
|
||||
context.GetSingletonType(SemIR::IntLiteralType::SingletonInstId));
|
||||
GetSingletonType(context, SemIR::IntLiteralType::SingletonInstId));
|
||||
context.AddInstAndPush<SemIR::ArrayType>(
|
||||
node_id, {.type_id = SemIR::TypeType::SingletonTypeId,
|
||||
.bound_id = bound_inst_id,
|
||||
|
||||
@@ -9,6 +9,7 @@
|
||||
#include "toolchain/check/name_lookup.h"
|
||||
#include "toolchain/check/return.h"
|
||||
#include "toolchain/check/subpattern.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/check/type_completion.h"
|
||||
#include "toolchain/diagnostics/format_providers.h"
|
||||
#include "toolchain/sem_ir/ids.h"
|
||||
@@ -124,7 +125,7 @@ static auto HandleAnyBindingPattern(Context& context, Parse::NodeId node_id,
|
||||
context.parse_tree().As<Parse::VarBindingPatternId>(node_id);
|
||||
auto& class_info = context.classes().Get(parent_class_decl->class_id);
|
||||
auto field_type_id =
|
||||
context.GetUnboundElementType(class_info.self_type_id, cast_type_id);
|
||||
GetUnboundElementType(context, class_info.self_type_id, cast_type_id);
|
||||
auto field_id = context.AddInst<SemIR::FieldDecl>(
|
||||
binding_id, {.type_id = field_type_id,
|
||||
.name_id = name_id,
|
||||
|
||||
@@ -16,6 +16,7 @@
|
||||
#include "toolchain/check/modifiers.h"
|
||||
#include "toolchain/check/name_component.h"
|
||||
#include "toolchain/check/name_lookup.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/check/type_completion.h"
|
||||
#include "toolchain/parse/node_ids.h"
|
||||
#include "toolchain/sem_ir/function.h"
|
||||
@@ -243,8 +244,8 @@ static auto BuildClassDecl(Context& context, Parse::AnyClassDeclId node_id,
|
||||
class_info.generic_id = BuildGenericDecl(context, class_decl_id);
|
||||
class_decl.class_id = context.classes().Add(class_info);
|
||||
if (class_info.has_parameters()) {
|
||||
class_decl.type_id = context.GetGenericClassType(
|
||||
class_decl.class_id, context.scope_stack().PeekSpecificId());
|
||||
class_decl.type_id = GetGenericClassType(
|
||||
context, class_decl.class_id, context.scope_stack().PeekSpecificId());
|
||||
}
|
||||
} else {
|
||||
FinishGenericRedecl(context, class_decl_id, class_info.generic_id);
|
||||
@@ -260,11 +261,12 @@ static auto BuildClassDecl(Context& context, Parse::AnyClassDeclId node_id,
|
||||
auto& class_info = context.classes().Get(class_decl.class_id);
|
||||
auto specific_id =
|
||||
context.generics().GetSelfSpecific(class_info.generic_id);
|
||||
class_info.self_type_id = context.GetTypeIdForTypeConstant(TryEvalInst(
|
||||
context, SemIR::InstId::None,
|
||||
SemIR::ClassType{.type_id = SemIR::TypeType::SingletonTypeId,
|
||||
.class_id = class_decl.class_id,
|
||||
.specific_id = specific_id}));
|
||||
class_info.self_type_id =
|
||||
context.types().GetTypeIdForTypeConstantId(TryEvalInst(
|
||||
context, SemIR::InstId::None,
|
||||
SemIR::ClassType{.type_id = SemIR::TypeType::SingletonTypeId,
|
||||
.class_id = class_decl.class_id,
|
||||
.specific_id = specific_id}));
|
||||
}
|
||||
|
||||
if (!is_definition && context.sem_ir().is_impl() && !is_extern) {
|
||||
@@ -542,8 +544,8 @@ auto HandleParseNode(Context& context, Parse::BaseDeclId node_id) -> bool {
|
||||
|
||||
// The `base` value in the class scope has an unbound element type. Instance
|
||||
// binding will be performed when it's found by name lookup into an instance.
|
||||
auto field_type_id =
|
||||
context.GetUnboundElementType(class_info.self_type_id, base_info.type_id);
|
||||
auto field_type_id = GetUnboundElementType(context, class_info.self_type_id,
|
||||
base_info.type_id);
|
||||
class_info.base_id = context.AddInst<SemIR::BaseDecl>(
|
||||
node_id, {.type_id = field_type_id,
|
||||
.base_type_inst_id = base_info.inst_id,
|
||||
@@ -628,9 +630,9 @@ static auto CheckCompleteAdapterClassType(Context& context,
|
||||
auto object_repr_id = context.types().GetObjectRepr(adapted_type_id);
|
||||
|
||||
return context.AddInst<SemIR::CompleteTypeWitness>(
|
||||
node_id,
|
||||
{.type_id = context.GetSingletonType(SemIR::WitnessType::SingletonInstId),
|
||||
.object_repr_id = object_repr_id});
|
||||
node_id, {.type_id = GetSingletonType(
|
||||
context, SemIR::WitnessType::SingletonInstId),
|
||||
.object_repr_id = object_repr_id});
|
||||
}
|
||||
|
||||
static auto AddStructTypeFields(
|
||||
@@ -689,8 +691,9 @@ static auto CheckCompleteClassType(Context& context, Parse::NodeId node_id,
|
||||
if (defining_vptr) {
|
||||
struct_type_fields.push_back(
|
||||
{.name_id = SemIR::NameId::Vptr,
|
||||
.type_id = context.GetPointerType(
|
||||
context.GetSingletonType(SemIR::VtableType::SingletonInstId))});
|
||||
.type_id = GetPointerType(
|
||||
context,
|
||||
GetSingletonType(context, SemIR::VtableType::SingletonInstId))});
|
||||
}
|
||||
if (base_type_id.has_value()) {
|
||||
auto base_decl = context.insts().GetAs<SemIR::BaseDecl>(class_info.base_id);
|
||||
@@ -745,16 +748,17 @@ static auto CheckCompleteClassType(Context& context, Parse::NodeId node_id,
|
||||
}
|
||||
}
|
||||
class_info.vtable_id = context.AddInst<SemIR::Vtable>(
|
||||
node_id, {.type_id = context.GetSingletonType(
|
||||
SemIR::VtableType::SingletonInstId),
|
||||
node_id, {.type_id = GetSingletonType(
|
||||
context, SemIR::VtableType::SingletonInstId),
|
||||
.virtual_functions_id = context.inst_blocks().Add(vtable)});
|
||||
}
|
||||
|
||||
return context.AddInst<SemIR::CompleteTypeWitness>(
|
||||
node_id,
|
||||
{.type_id = context.GetSingletonType(SemIR::WitnessType::SingletonInstId),
|
||||
.object_repr_id = context.GetStructType(
|
||||
AddStructTypeFields(context, struct_type_fields))});
|
||||
{.type_id =
|
||||
GetSingletonType(context, SemIR::WitnessType::SingletonInstId),
|
||||
.object_repr_id = GetStructType(
|
||||
context, AddStructTypeFields(context, struct_type_fields))});
|
||||
}
|
||||
|
||||
auto HandleParseNode(Context& context, Parse::ClassDefinitionId node_id)
|
||||
|
||||
@@ -19,6 +19,7 @@
|
||||
#include "toolchain/check/modifiers.h"
|
||||
#include "toolchain/check/name_component.h"
|
||||
#include "toolchain/check/name_lookup.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/check/type_completion.h"
|
||||
#include "toolchain/sem_ir/builtin_function_kind.h"
|
||||
#include "toolchain/sem_ir/entry_point.h"
|
||||
@@ -309,8 +310,9 @@ static auto BuildFunctionDecl(Context& context,
|
||||
FinishGenericRedecl(context, decl_id, function_info.generic_id);
|
||||
// TODO: Validate that the redeclaration doesn't set an access modifier.
|
||||
}
|
||||
function_decl.type_id = context.GetFunctionType(
|
||||
function_decl.function_id, context.scope_stack().PeekSpecificId());
|
||||
function_decl.type_id =
|
||||
GetFunctionType(context, function_decl.function_id,
|
||||
context.scope_stack().PeekSpecificId());
|
||||
|
||||
// Write the function ID into the FunctionDecl.
|
||||
context.ReplaceInstBeforeConstantUse(decl_id, function_decl);
|
||||
@@ -351,7 +353,7 @@ static auto BuildFunctionDecl(Context& context,
|
||||
!function_info.param_patterns_id.has_value() ||
|
||||
!context.inst_blocks().Get(function_info.param_patterns_id).empty() ||
|
||||
(return_type_id.has_value() &&
|
||||
return_type_id != context.GetTupleType({}) &&
|
||||
return_type_id != GetTupleType(context, {}) &&
|
||||
// TODO: Decide on valid return types for `Main.Run`. Perhaps we should
|
||||
// have an interface for this.
|
||||
return_type_id != MakeIntType(context, node_id, SemIR::IntKind::Signed,
|
||||
@@ -548,7 +550,7 @@ static auto IsValidBuiltinDeclaration(Context& context,
|
||||
// Get the return type. This is `()` if none was specified.
|
||||
auto return_type_id = function.GetDeclaredReturnType(context.sem_ir());
|
||||
if (!return_type_id.has_value()) {
|
||||
return_type_id = context.GetTupleType({});
|
||||
return_type_id = GetTupleType(context, {});
|
||||
}
|
||||
|
||||
return builtin_kind.IsValidType(context.sem_ir(), param_type_ids,
|
||||
|
||||
@@ -12,6 +12,7 @@
|
||||
#include "toolchain/check/modifiers.h"
|
||||
#include "toolchain/check/name_lookup.h"
|
||||
#include "toolchain/check/pattern_match.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/parse/typed_nodes.h"
|
||||
#include "toolchain/sem_ir/generic.h"
|
||||
#include "toolchain/sem_ir/ids.h"
|
||||
@@ -307,7 +308,7 @@ static auto BuildImplDecl(Context& context, Parse::AnyImplDeclId node_id,
|
||||
context.node_stack().PopExprWithNodeId();
|
||||
auto [self_type_node, self_inst_id] =
|
||||
context.node_stack().PopWithNodeId<Parse::NodeCategory::ImplAs>();
|
||||
auto self_type_id = context.GetTypeIdForTypeInst(self_inst_id);
|
||||
auto self_type_id = context.types().GetTypeIdForTypeInstId(self_inst_id);
|
||||
// Pop the `impl` introducer and any `forall` parameters as a "name".
|
||||
auto name = PopImplIntroducerAndParamsAsNameComponent(context, node_id);
|
||||
auto decl_block_id = context.inst_block_stack().Pop();
|
||||
|
||||
@@ -11,6 +11,7 @@
|
||||
#include "toolchain/check/literal.h"
|
||||
#include "toolchain/check/name_lookup.h"
|
||||
#include "toolchain/check/operator.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/diagnostics/diagnostic.h"
|
||||
#include "toolchain/sem_ir/inst.h"
|
||||
#include "toolchain/sem_ir/typed_insts.h"
|
||||
@@ -53,9 +54,10 @@ static auto GetIndexWithArgs(Context& context, Parse::NodeId node_id,
|
||||
}
|
||||
|
||||
for (const auto& impl : context.impls().array_ref()) {
|
||||
auto impl_self_type_id = context.GetTypeIdForTypeInst(impl.self_id);
|
||||
auto impl_self_type_id =
|
||||
context.types().GetTypeIdForTypeInstId(impl.self_id);
|
||||
auto impl_constraint_type_id =
|
||||
context.GetTypeIdForTypeInst(impl.constraint_id);
|
||||
context.types().GetTypeIdForTypeInstId(impl.constraint_id);
|
||||
|
||||
if (impl_self_type_id != self_id) {
|
||||
continue;
|
||||
@@ -115,7 +117,7 @@ static auto PerformIndexWith(Context& context, Parse::NodeId node_id,
|
||||
|
||||
// The first argument of the `IndexWith` interface corresponds to the
|
||||
// `SubscriptType`, so first cast `index_inst_id` to that type.
|
||||
auto subscript_type_id = context.GetTypeIdForTypeInst((*args)[0]);
|
||||
auto subscript_type_id = context.types().GetTypeIdForTypeInstId((*args)[0]);
|
||||
auto cast_index_id =
|
||||
ConvertToValueOfType(context, node_id, index_inst_id, subscript_type_id);
|
||||
|
||||
|
||||
@@ -10,6 +10,7 @@
|
||||
#include "toolchain/check/modifiers.h"
|
||||
#include "toolchain/check/name_component.h"
|
||||
#include "toolchain/check/name_lookup.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/sem_ir/typed_insts.h"
|
||||
|
||||
namespace Carbon::Check {
|
||||
@@ -116,8 +117,9 @@ static auto BuildInterfaceDecl(Context& context,
|
||||
interface_info.generic_id = BuildGenericDecl(context, interface_decl_id);
|
||||
interface_decl.interface_id = context.interfaces().Add(interface_info);
|
||||
if (interface_info.has_parameters()) {
|
||||
interface_decl.type_id = context.GetGenericInterfaceType(
|
||||
interface_decl.interface_id, context.scope_stack().PeekSpecificId());
|
||||
interface_decl.type_id =
|
||||
GetGenericInterfaceType(context, interface_decl.interface_id,
|
||||
context.scope_stack().PeekSpecificId());
|
||||
}
|
||||
} else {
|
||||
FinishGenericRedecl(
|
||||
@@ -163,8 +165,8 @@ auto HandleParseNode(Context& context,
|
||||
|
||||
// Declare and introduce `Self`.
|
||||
SemIR::FacetType facet_type =
|
||||
context.FacetTypeFromInterface(interface_id, self_specific_id);
|
||||
SemIR::TypeId self_type_id = context.GetTypeIdForTypeConstant(
|
||||
FacetTypeFromInterface(context, interface_id, self_specific_id);
|
||||
SemIR::TypeId self_type_id = context.types().GetTypeIdForTypeConstantId(
|
||||
TryEvalInst(context, SemIR::InstId::None, facet_type));
|
||||
|
||||
// We model `Self` as a symbolic binding whose type is the interface.
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
#include "toolchain/check/handle.h"
|
||||
#include "toolchain/check/literal.h"
|
||||
#include "toolchain/check/name_lookup.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/diagnostics/format_providers.h"
|
||||
#include "toolchain/sem_ir/typed_insts.h"
|
||||
|
||||
@@ -16,7 +17,7 @@ auto HandleParseNode(Context& context, Parse::BoolLiteralFalseId node_id)
|
||||
-> bool {
|
||||
context.AddInstAndPush<SemIR::BoolLiteral>(
|
||||
node_id,
|
||||
{.type_id = context.GetSingletonType(SemIR::BoolType::SingletonInstId),
|
||||
{.type_id = GetSingletonType(context, SemIR::BoolType::SingletonInstId),
|
||||
.value = SemIR::BoolValue::False});
|
||||
return true;
|
||||
}
|
||||
@@ -25,7 +26,7 @@ auto HandleParseNode(Context& context, Parse::BoolLiteralTrueId node_id)
|
||||
-> bool {
|
||||
context.AddInstAndPush<SemIR::BoolLiteral>(
|
||||
node_id,
|
||||
{.type_id = context.GetSingletonType(SemIR::BoolType::SingletonInstId),
|
||||
{.type_id = GetSingletonType(context, SemIR::BoolType::SingletonInstId),
|
||||
.value = SemIR::BoolValue::True});
|
||||
return true;
|
||||
}
|
||||
@@ -76,8 +77,8 @@ auto HandleParseNode(Context& context, Parse::RealLiteralId node_id) -> bool {
|
||||
|
||||
auto float_id = context.sem_ir().floats().Add(llvm::APFloat(double_val));
|
||||
context.AddInstAndPush<SemIR::FloatLiteral>(
|
||||
node_id, {.type_id = context.GetSingletonType(
|
||||
SemIR::LegacyFloatType::SingletonInstId),
|
||||
node_id, {.type_id = GetSingletonType(
|
||||
context, SemIR::LegacyFloatType::SingletonInstId),
|
||||
.float_id = float_id});
|
||||
return true;
|
||||
}
|
||||
@@ -85,7 +86,7 @@ auto HandleParseNode(Context& context, Parse::RealLiteralId node_id) -> bool {
|
||||
auto HandleParseNode(Context& context, Parse::StringLiteralId node_id) -> bool {
|
||||
context.AddInstAndPush<SemIR::StringLiteral>(
|
||||
node_id,
|
||||
{.type_id = context.GetSingletonType(SemIR::StringType::SingletonInstId),
|
||||
{.type_id = GetSingletonType(context, SemIR::StringType::SingletonInstId),
|
||||
.string_literal_id = context.tokens().GetStringLiteralValue(
|
||||
context.parse_tree().node_token(node_id))});
|
||||
return true;
|
||||
|
||||
@@ -9,6 +9,7 @@
|
||||
#include "toolchain/check/name_component.h"
|
||||
#include "toolchain/check/name_lookup.h"
|
||||
#include "toolchain/check/pointer_dereference.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/lex/token_kind.h"
|
||||
#include "toolchain/sem_ir/inst.h"
|
||||
#include "toolchain/sem_ir/typed_insts.h"
|
||||
@@ -238,8 +239,8 @@ auto HandleParseNode(Context& context, Parse::DesignatorExprId node_id)
|
||||
|
||||
auto HandleParseNode(Context& context, Parse::PackageExprId node_id) -> bool {
|
||||
context.AddInstAndPush<SemIR::NameRef>(
|
||||
node_id, {.type_id = context.GetSingletonType(
|
||||
SemIR::NamespaceType::SingletonInstId),
|
||||
node_id, {.type_id = GetSingletonType(
|
||||
context, SemIR::NamespaceType::SingletonInstId),
|
||||
.name_id = SemIR::NameId::PackageNamespace,
|
||||
.value_id = SemIR::Namespace::PackageInstId});
|
||||
return true;
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
#include "toolchain/check/modifiers.h"
|
||||
#include "toolchain/check/name_component.h"
|
||||
#include "toolchain/check/name_lookup.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/sem_ir/ids.h"
|
||||
#include "toolchain/sem_ir/inst.h"
|
||||
#include "toolchain/sem_ir/name_scope.h"
|
||||
@@ -38,7 +39,7 @@ auto HandleParseNode(Context& context, Parse::NamespaceId node_id) -> bool {
|
||||
LimitModifiersOnDecl(context, introducer, KeywordModifierSet::None);
|
||||
|
||||
auto namespace_inst = SemIR::Namespace{
|
||||
context.GetSingletonType(SemIR::NamespaceType::SingletonInstId),
|
||||
GetSingletonType(context, SemIR::NamespaceType::SingletonInstId),
|
||||
SemIR::NameScopeId::None, SemIR::InstId::None};
|
||||
auto namespace_id =
|
||||
context.AddPlaceholderInst(SemIR::LocIdAndInst(node_id, namespace_inst));
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
#include "toolchain/check/handle.h"
|
||||
#include "toolchain/check/operator.h"
|
||||
#include "toolchain/check/pointer_dereference.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/diagnostics/diagnostic_emitter.h"
|
||||
|
||||
namespace Carbon::Check {
|
||||
@@ -244,7 +245,7 @@ auto HandleParseNode(Context& context, Parse::PrefixOperatorAmpId node_id)
|
||||
break;
|
||||
}
|
||||
context.AddInstAndPush<SemIR::AddrOf>(
|
||||
node_id, SemIR::AddrOf{.type_id = context.GetPointerType(type_id),
|
||||
node_id, SemIR::AddrOf{.type_id = GetPointerType(context, type_id),
|
||||
.lvalue_id = value_id});
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -6,6 +6,7 @@
|
||||
#include "toolchain/check/context.h"
|
||||
#include "toolchain/check/convert.h"
|
||||
#include "toolchain/check/handle.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/diagnostics/format_providers.h"
|
||||
|
||||
namespace Carbon::Check {
|
||||
@@ -141,8 +142,8 @@ auto HandleParseNode(Context& context, Parse::StructLiteralId node_id) -> bool {
|
||||
/*is_struct_type_literal=*/false)) {
|
||||
context.node_stack().Push(node_id, SemIR::ErrorInst::SingletonInstId);
|
||||
} else {
|
||||
auto type_id = context.GetStructType(
|
||||
context.struct_type_fields().AddCanonical(fields));
|
||||
auto type_id = GetStructType(
|
||||
context, context.struct_type_fields().AddCanonical(fields));
|
||||
|
||||
auto value_id = context.AddInst<SemIR::StructLiteral>(
|
||||
node_id, {.type_id = type_id, .elements_id = elements_id});
|
||||
|
||||
@@ -4,6 +4,7 @@
|
||||
|
||||
#include "toolchain/check/context.h"
|
||||
#include "toolchain/check/handle.h"
|
||||
#include "toolchain/check/type.h"
|
||||
|
||||
namespace Carbon::Check {
|
||||
|
||||
@@ -32,7 +33,7 @@ auto HandleParseNode(Context& context, Parse::TupleLiteralId node_id) -> bool {
|
||||
for (auto inst : inst_block) {
|
||||
type_ids.push_back(context.insts().Get(inst).type_id());
|
||||
}
|
||||
auto type_id = context.GetTupleType(type_ids);
|
||||
auto type_id = GetTupleType(context, type_ids);
|
||||
|
||||
auto value_id = context.AddInst<SemIR::TupleLiteral>(
|
||||
node_id, {.type_id = type_id, .elements_id = refs_id});
|
||||
|
||||
@@ -17,7 +17,7 @@ auto HandleParseNode(Context& context, Parse::WhereOperandId node_id) -> bool {
|
||||
auto self_type_id = ExprAsType(context, self_node, self_id).type_id;
|
||||
// Only facet types may have `where` restrictions.
|
||||
if (self_type_id != SemIR::ErrorInst::SingletonTypeId &&
|
||||
!context.IsFacetType(self_type_id)) {
|
||||
!context.types().IsFacetType(self_type_id)) {
|
||||
CARBON_DIAGNOSTIC(WhereOnNonFacetType, Error,
|
||||
"left argument of `where` operator must be a facet type");
|
||||
context.emitter().Emit(self_node, WhereOnNonFacetType);
|
||||
@@ -107,7 +107,7 @@ auto HandleParseNode(Context& context, Parse::RequirementImplsId node_id)
|
||||
auto lhs_as_type = ExprAsType(context, lhs_node, lhs_id);
|
||||
auto rhs_as_type = ExprAsType(context, rhs_node, rhs_id);
|
||||
if (rhs_as_type.type_id != SemIR::ErrorInst::SingletonTypeId &&
|
||||
!context.IsFacetType(rhs_as_type.type_id)) {
|
||||
!context.types().IsFacetType(rhs_as_type.type_id)) {
|
||||
CARBON_DIAGNOSTIC(
|
||||
ImplsOnNonFacetType, Error,
|
||||
"right argument of `impls` requirement must be a facet type");
|
||||
|
||||
@@ -13,6 +13,7 @@
|
||||
#include "toolchain/check/import_ref.h"
|
||||
#include "toolchain/check/interface.h"
|
||||
#include "toolchain/check/name_lookup.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/check/type_completion.h"
|
||||
#include "toolchain/diagnostics/diagnostic_emitter.h"
|
||||
#include "toolchain/sem_ir/generic.h"
|
||||
@@ -85,7 +86,8 @@ auto ImplWitnessForDeclaration(Context& context, const SemIR::Impl& impl)
|
||||
-> SemIR::InstId {
|
||||
CARBON_CHECK(!impl.has_definition_started());
|
||||
|
||||
auto facet_type_id = context.GetTypeIdForTypeInst(impl.constraint_id);
|
||||
auto facet_type_id =
|
||||
context.types().GetTypeIdForTypeInstId(impl.constraint_id);
|
||||
if (facet_type_id == SemIR::ErrorInst::SingletonTypeId) {
|
||||
return SemIR::ErrorInst::SingletonInstId;
|
||||
}
|
||||
@@ -133,7 +135,8 @@ auto ImplWitnessForDeclaration(Context& context, const SemIR::Impl& impl)
|
||||
auto table_id = context.inst_blocks().Add(table);
|
||||
return context.AddInst<SemIR::ImplWitness>(
|
||||
context.insts().GetLocId(impl.latest_decl_id()),
|
||||
{.type_id = context.GetSingletonType(SemIR::WitnessType::SingletonInstId),
|
||||
{.type_id =
|
||||
GetSingletonType(context, SemIR::WitnessType::SingletonInstId),
|
||||
.elements_id = table_id,
|
||||
.specific_id = context.generics().GetSelfSpecific(impl.generic_id)});
|
||||
}
|
||||
@@ -162,7 +165,8 @@ auto AddConstantsToImplWitnessFromConstraint(Context& context,
|
||||
if (witness_id == SemIR::ErrorInst::SingletonInstId) {
|
||||
return;
|
||||
}
|
||||
auto facet_type_id = context.GetTypeIdForTypeInst(impl.constraint_id);
|
||||
auto facet_type_id =
|
||||
context.types().GetTypeIdForTypeInstId(impl.constraint_id);
|
||||
CARBON_CHECK(facet_type_id != SemIR::ErrorInst::SingletonTypeId);
|
||||
auto facet_type = context.types().GetAs<SemIR::FacetType>(facet_type_id);
|
||||
const SemIR::FacetTypeInfo& facet_type_info =
|
||||
@@ -239,7 +243,7 @@ auto AddConstantsToImplWitnessFromConstraint(Context& context,
|
||||
// value for `Self`.
|
||||
assoc_const_type_id = GetTypeForSpecificAssociatedEntity(
|
||||
context, impl.constraint_id, interface_type->specific_id, decl_id,
|
||||
context.GetTypeIdForTypeInst(impl.self_id), witness_id);
|
||||
context.types().GetTypeIdForTypeInstId(impl.self_id), witness_id);
|
||||
|
||||
// Perform the conversion of the value to the type. We skipped this when
|
||||
// forming the facet type because the type of the associated constant
|
||||
@@ -283,7 +287,8 @@ auto ImplWitnessStartDefinition(Context& context, SemIR::Impl& impl) -> void {
|
||||
return;
|
||||
}
|
||||
|
||||
auto facet_type_id = context.GetTypeIdForTypeInst(impl.constraint_id);
|
||||
auto facet_type_id =
|
||||
context.types().GetTypeIdForTypeInstId(impl.constraint_id);
|
||||
CARBON_CHECK(facet_type_id != SemIR::ErrorInst::SingletonTypeId);
|
||||
auto facet_type = context.types().GetAs<SemIR::FacetType>(facet_type_id);
|
||||
const SemIR::FacetTypeInfo& facet_type_info =
|
||||
@@ -340,7 +345,8 @@ auto FinishImplWitness(Context& context, SemIR::Impl& impl) -> void {
|
||||
return;
|
||||
}
|
||||
|
||||
auto facet_type_id = context.GetTypeIdForTypeInst(impl.constraint_id);
|
||||
auto facet_type_id =
|
||||
context.types().GetTypeIdForTypeInstId(impl.constraint_id);
|
||||
CARBON_CHECK(facet_type_id != SemIR::ErrorInst::SingletonTypeId);
|
||||
auto facet_type = context.types().GetAs<SemIR::FacetType>(facet_type_id);
|
||||
const SemIR::FacetTypeInfo& facet_type_info =
|
||||
@@ -354,7 +360,7 @@ auto FinishImplWitness(Context& context, SemIR::Impl& impl) -> void {
|
||||
auto witness = context.insts().GetAs<SemIR::ImplWitness>(impl.witness_id);
|
||||
auto witness_block = context.inst_blocks().GetMutable(witness.elements_id);
|
||||
auto& impl_scope = context.name_scopes().Get(impl.scope_id);
|
||||
auto self_type_id = context.GetTypeIdForTypeInst(impl.self_id);
|
||||
auto self_type_id = context.types().GetTypeIdForTypeInstId(impl.self_id);
|
||||
auto assoc_entities =
|
||||
context.inst_blocks().Get(interface.associated_entities_id);
|
||||
llvm::SmallVector<SemIR::InstId> used_decl_ids;
|
||||
|
||||
@@ -11,6 +11,7 @@
|
||||
#include "toolchain/check/import_ref.h"
|
||||
#include "toolchain/check/merge.h"
|
||||
#include "toolchain/check/name_lookup.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/parse/node_ids.h"
|
||||
#include "toolchain/sem_ir/file.h"
|
||||
#include "toolchain/sem_ir/ids.h"
|
||||
@@ -508,7 +509,7 @@ static auto AddNamespaceFromOtherPackage(Context& context,
|
||||
SemIR::NameId name_id)
|
||||
-> SemIR::InstId {
|
||||
auto namespace_type_id =
|
||||
context.GetSingletonType(SemIR::NamespaceType::SingletonInstId);
|
||||
GetSingletonType(context, SemIR::NamespaceType::SingletonInstId);
|
||||
AddImportNamespaceResult result = CopySingleNameScopeFromImportIR(
|
||||
context, namespace_type_id, /*copied_namespaces=*/nullptr, import_ir_id,
|
||||
import_inst_id, import_ns.name_scope_id, parent_scope_id, name_id);
|
||||
|
||||
@@ -17,6 +17,7 @@
|
||||
#include "toolchain/check/context.h"
|
||||
#include "toolchain/check/diagnostic_helpers.h"
|
||||
#include "toolchain/check/import.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/diagnostics/diagnostic.h"
|
||||
#include "toolchain/diagnostics/format_providers.h"
|
||||
#include "toolchain/sem_ir/name_scope.h"
|
||||
@@ -99,7 +100,7 @@ static auto AddNamespace(Context& context, PackageNameId cpp_package_id,
|
||||
|
||||
return AddImportNamespace(
|
||||
context,
|
||||
context.GetSingletonType(SemIR::NamespaceType::SingletonInstId),
|
||||
GetSingletonType(context, SemIR::NamespaceType::SingletonInstId),
|
||||
SemIR::NameId::ForPackageName(cpp_package_id),
|
||||
SemIR::NameScopeId::Package,
|
||||
/*diagnose_duplicate_namespace=*/false,
|
||||
|
||||
@@ -10,6 +10,7 @@
|
||||
#include "toolchain/check/eval.h"
|
||||
#include "toolchain/check/generic.h"
|
||||
#include "toolchain/check/name_lookup.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/parse/node_ids.h"
|
||||
#include "toolchain/sem_ir/constant.h"
|
||||
#include "toolchain/sem_ir/file.h"
|
||||
@@ -520,9 +521,9 @@ class ImportRefResolver : public ImportContext {
|
||||
import_ir().constant_values().GetInstId(import_type_const_id);
|
||||
SemIR::IsSingletonInstId(import_type_inst_id)) {
|
||||
// Builtins don't require constant resolution; we can use them directly.
|
||||
return local_context().GetSingletonType(import_type_inst_id);
|
||||
return GetSingletonType(local_context(), import_type_inst_id);
|
||||
} else {
|
||||
return local_context().GetTypeIdForTypeConstant(
|
||||
return local_context().types().GetTypeIdForTypeConstantId(
|
||||
ResolveConstant(import_type_id.AsConstantId()));
|
||||
}
|
||||
}
|
||||
@@ -1023,7 +1024,7 @@ static auto GetLocalParamPatternsId(ImportContext& context,
|
||||
auto entity_name =
|
||||
context.import_entity_names().Get(binding.entity_name_id);
|
||||
auto name_id = GetLocalNameId(context, entity_name.name_id);
|
||||
auto type_id = context.local_context().GetTypeIdForTypeConstant(
|
||||
auto type_id = context.local_context().types().GetTypeIdForTypeConstantId(
|
||||
GetLocalConstantIdChecked(context, binding.type_id));
|
||||
|
||||
auto new_param_id = SemIR::InstId::None;
|
||||
@@ -1062,7 +1063,7 @@ static auto GetLocalParamPatternsId(ImportContext& context,
|
||||
.subpattern_id = new_param_id,
|
||||
.runtime_index = param_pattern.runtime_index}));
|
||||
if (addr_inst) {
|
||||
type_id = context.local_context().GetTypeIdForTypeConstant(
|
||||
type_id = context.local_context().types().GetTypeIdForTypeConstantId(
|
||||
GetLocalConstantIdChecked(context, addr_inst->type_id));
|
||||
new_param_id = context.local_context().AddInstInNoBlock(
|
||||
context.local_context().MakeImportedLocAndInst<SemIR::AddrPattern>(
|
||||
@@ -1093,7 +1094,7 @@ static auto GetLocalReturnSlotPatternId(
|
||||
auto return_slot_pattern =
|
||||
context.import_insts().GetAs<SemIR::ReturnSlotPattern>(
|
||||
param_pattern.subpattern_id);
|
||||
auto type_id = context.local_context().GetTypeIdForTypeConstant(
|
||||
auto type_id = context.local_context().types().GetTypeIdForTypeConstantId(
|
||||
GetLocalConstantIdChecked(context, return_slot_pattern.type_id));
|
||||
|
||||
auto new_return_slot_pattern_id = context.local_context().AddInstInNoBlock(
|
||||
@@ -1357,7 +1358,8 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
}
|
||||
|
||||
auto element_type_id =
|
||||
resolver.local_context().GetTypeIdForTypeConstant(element_type_const_id);
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(
|
||||
element_type_const_id);
|
||||
return ResolveAs<SemIR::ArrayType>(
|
||||
resolver, {.type_id = SemIR::TypeType::SingletonTypeId,
|
||||
.bound_id = bound_id,
|
||||
@@ -1412,8 +1414,8 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
}
|
||||
|
||||
// In the second phase, create the associated constant and its declaration.
|
||||
auto type_id =
|
||||
resolver.local_context().GetTypeIdForTypeConstant(type_const_id);
|
||||
auto type_id = resolver.local_context().types().GetTypeIdForTypeConstantId(
|
||||
type_const_id);
|
||||
std::tie(assoc_const_id, const_id) =
|
||||
MakeAssociatedConstant(resolver, import_assoc_const, type_id);
|
||||
} else {
|
||||
@@ -1456,10 +1458,11 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
auto decl_id = AddImportRef(resolver, inst.decl_id);
|
||||
|
||||
return ResolveAs<SemIR::AssociatedEntity>(
|
||||
resolver, {.type_id = resolver.local_context().GetTypeIdForTypeConstant(
|
||||
type_const_id),
|
||||
.index = inst.index,
|
||||
.decl_id = decl_id});
|
||||
resolver,
|
||||
{.type_id = resolver.local_context().types().GetTypeIdForTypeConstantId(
|
||||
type_const_id),
|
||||
.index = inst.index,
|
||||
.decl_id = decl_id});
|
||||
}
|
||||
|
||||
static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
@@ -1475,8 +1478,9 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
return ResolveAs<SemIR::AssociatedEntityType>(
|
||||
resolver,
|
||||
{.type_id = SemIR::TypeType::SingletonTypeId,
|
||||
.interface_type_id = resolver.local_context().GetTypeIdForTypeConstant(
|
||||
interface_inst_id)});
|
||||
.interface_type_id =
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(
|
||||
interface_inst_id)});
|
||||
}
|
||||
|
||||
static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
@@ -1498,7 +1502,8 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
resolver.local_context().MakeImportedLocAndInst<SemIR::BaseDecl>(
|
||||
AddImportIRInst(resolver, import_inst_id),
|
||||
{.type_id =
|
||||
resolver.local_context().GetTypeIdForTypeConstant(type_const_id),
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(
|
||||
type_const_id),
|
||||
.base_type_inst_id = base_type_inst_id,
|
||||
.index = inst.index}));
|
||||
return ResolveResult::Done(resolver.local_constant_values().Get(inst_id),
|
||||
@@ -1517,9 +1522,10 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver, SemIR::Vtable inst)
|
||||
auto virtual_functions_id = GetLocalCanonicalInstBlockId(
|
||||
resolver, inst.virtual_functions_id, virtual_functions);
|
||||
return ResolveAs<SemIR::Vtable>(
|
||||
resolver, {.type_id = resolver.local_context().GetTypeIdForTypeConstant(
|
||||
type_const_id),
|
||||
.virtual_functions_id = virtual_functions_id});
|
||||
resolver,
|
||||
{.type_id = resolver.local_context().types().GetTypeIdForTypeConstantId(
|
||||
type_const_id),
|
||||
.virtual_functions_id = virtual_functions_id});
|
||||
}
|
||||
|
||||
static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
@@ -1545,7 +1551,8 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
import_entity_name.is_template);
|
||||
return ResolveAs<SemIR::BindSymbolicName>(
|
||||
resolver,
|
||||
{.type_id = resolver.local_context().GetTypeIdForTypeConstant(type_id),
|
||||
{.type_id =
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(type_id),
|
||||
.entity_name_id = entity_name_id,
|
||||
.value_id = SemIR::InstId::None});
|
||||
}
|
||||
@@ -1568,7 +1575,8 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
import_entity_name.is_template);
|
||||
return ResolveAs<SemIR::SymbolicBindingPattern>(
|
||||
resolver,
|
||||
{.type_id = resolver.local_context().GetTypeIdForTypeConstant(type_id),
|
||||
{.type_id =
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(type_id),
|
||||
.entity_name_id = entity_name_id});
|
||||
}
|
||||
|
||||
@@ -1585,10 +1593,11 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
}
|
||||
|
||||
return ResolveAs<SemIR::BoundMethod>(
|
||||
resolver, {.type_id = resolver.local_context().GetSingletonType(
|
||||
SemIR::BoundMethodType::SingletonInstId),
|
||||
.object_id = object_id,
|
||||
.function_decl_id = function_decl_id});
|
||||
resolver,
|
||||
{.type_id = GetSingletonType(resolver.local_context(),
|
||||
SemIR::BoundMethodType::SingletonInstId),
|
||||
.object_id = object_id,
|
||||
.function_decl_id = function_decl_id});
|
||||
}
|
||||
|
||||
static auto TryResolveTypedInst(ImportRefResolver& resolver, SemIR::Call inst)
|
||||
@@ -1603,7 +1612,8 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver, SemIR::Call inst)
|
||||
|
||||
return ResolveAs<SemIR::Call>(
|
||||
resolver,
|
||||
{.type_id = resolver.local_context().GetTypeIdForTypeConstant(type_id),
|
||||
{.type_id =
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(type_id),
|
||||
.callee_id = callee_id,
|
||||
.args_id = GetLocalCanonicalInstBlockId(resolver, inst.args_id, args)});
|
||||
}
|
||||
@@ -1630,8 +1640,8 @@ static auto MakeIncompleteClass(ImportContext& context,
|
||||
.is_dynamic = import_class.is_dynamic}});
|
||||
|
||||
if (import_class.has_parameters()) {
|
||||
class_decl.type_id = context.local_context().GetGenericClassType(
|
||||
class_decl.class_id, enclosing_specific_id);
|
||||
class_decl.type_id = GetGenericClassType(
|
||||
context.local_context(), class_decl.class_id, enclosing_specific_id);
|
||||
}
|
||||
|
||||
// Write the class ID into the ClassDecl.
|
||||
@@ -1756,13 +1766,14 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
SetGenericData(resolver, import_class.generic_id, new_class.generic_id,
|
||||
generic_data);
|
||||
new_class.self_type_id =
|
||||
resolver.local_context().GetTypeIdForTypeConstant(self_const_id);
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(
|
||||
self_const_id);
|
||||
|
||||
if (import_class.is_defined()) {
|
||||
auto complete_type_witness_id = AddLoadedImportRef(
|
||||
resolver,
|
||||
resolver.local_context().GetSingletonType(
|
||||
SemIR::WitnessType::SingletonInstId),
|
||||
GetSingletonType(resolver.local_context(),
|
||||
SemIR::WitnessType::SingletonInstId),
|
||||
import_class.complete_type_witness_id, complete_type_witness_const_id);
|
||||
AddClassDefinition(resolver, import_class, new_class,
|
||||
complete_type_witness_id, base_id, adapt_id, vtable_id);
|
||||
@@ -1812,11 +1823,13 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
return ResolveResult::Retry();
|
||||
}
|
||||
auto object_repr_id =
|
||||
resolver.local_context().GetTypeIdForTypeConstant(object_repr_const_id);
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(
|
||||
object_repr_const_id);
|
||||
return ResolveAs<SemIR::CompleteTypeWitness>(
|
||||
resolver, {.type_id = resolver.local_context().GetSingletonType(
|
||||
SemIR::WitnessType::SingletonInstId),
|
||||
.object_repr_id = object_repr_id});
|
||||
resolver,
|
||||
{.type_id = GetSingletonType(resolver.local_context(),
|
||||
SemIR::WitnessType::SingletonInstId),
|
||||
.object_repr_id = object_repr_id});
|
||||
}
|
||||
|
||||
static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
@@ -1827,7 +1840,8 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
return ResolveResult::Retry();
|
||||
}
|
||||
auto inner_type_id =
|
||||
resolver.local_context().GetTypeIdForTypeConstant(inner_const_id);
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(
|
||||
inner_const_id);
|
||||
return ResolveAs<SemIR::ConstType>(
|
||||
resolver,
|
||||
{.type_id = SemIR::TypeType::SingletonTypeId, .inner_id = inner_type_id});
|
||||
@@ -1850,7 +1864,8 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
resolver.local_context().MakeImportedLocAndInst<SemIR::FieldDecl>(
|
||||
AddImportIRInst(resolver, import_inst_id),
|
||||
{.type_id =
|
||||
resolver.local_context().GetTypeIdForTypeConstant(const_id),
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(
|
||||
const_id),
|
||||
.name_id = GetLocalNameId(resolver, inst.name_id),
|
||||
.index = inst.index}));
|
||||
return ResolveResult::Done(resolver.local_constant_values().Get(inst_id),
|
||||
@@ -1878,8 +1893,8 @@ static auto MakeFunctionDecl(ImportContext& context,
|
||||
{.return_slot_pattern_id = SemIR::InstId::None,
|
||||
.builtin_function_kind = import_function.builtin_function_kind}});
|
||||
|
||||
function_decl.type_id = context.local_context().GetFunctionType(
|
||||
function_decl.function_id, specific_id);
|
||||
function_decl.type_id = GetFunctionType(
|
||||
context.local_context(), function_decl.function_id, specific_id);
|
||||
|
||||
// Write the function ID and type into the FunctionDecl.
|
||||
context.local_context().ReplaceInstBeforeConstantUse(function_decl_id,
|
||||
@@ -2199,8 +2214,9 @@ static auto MakeInterfaceDecl(ImportContext& context,
|
||||
{}});
|
||||
|
||||
if (import_interface.has_parameters()) {
|
||||
interface_decl.type_id = context.local_context().GetGenericInterfaceType(
|
||||
interface_decl.interface_id, enclosing_specific_id);
|
||||
interface_decl.type_id = GetGenericInterfaceType(
|
||||
context.local_context(), interface_decl.interface_id,
|
||||
enclosing_specific_id);
|
||||
}
|
||||
|
||||
// Write the interface ID into the InterfaceDecl.
|
||||
@@ -2341,9 +2357,10 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
}
|
||||
|
||||
return ResolveAs<SemIR::FacetAccessWitness>(
|
||||
resolver, {.type_id = resolver.local_context().GetSingletonType(
|
||||
SemIR::WitnessType::SingletonInstId),
|
||||
.facet_value_inst_id = facet_value_inst_id});
|
||||
resolver,
|
||||
{.type_id = GetSingletonType(resolver.local_context(),
|
||||
SemIR::WitnessType::SingletonInstId),
|
||||
.facet_value_inst_id = facet_value_inst_id});
|
||||
}
|
||||
|
||||
static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
@@ -2423,7 +2440,8 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
|
||||
return ResolveAs<SemIR::FacetValue>(
|
||||
resolver,
|
||||
{.type_id = resolver.local_context().GetTypeIdForTypeConstant(type_id),
|
||||
{.type_id =
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(type_id),
|
||||
.type_inst_id = type_inst_id,
|
||||
.witness_inst_id = witness_inst_id});
|
||||
}
|
||||
@@ -2439,10 +2457,11 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
auto specific_id =
|
||||
GetOrAddLocalSpecific(resolver, inst.specific_id, specific_data);
|
||||
return ResolveAs<SemIR::ImplWitness>(
|
||||
resolver, {.type_id = resolver.local_context().GetSingletonType(
|
||||
SemIR::WitnessType::SingletonInstId),
|
||||
.elements_id = elements_id,
|
||||
.specific_id = specific_id});
|
||||
resolver,
|
||||
{.type_id = GetSingletonType(resolver.local_context(),
|
||||
SemIR::WitnessType::SingletonInstId),
|
||||
.elements_id = elements_id,
|
||||
.specific_id = specific_id});
|
||||
}
|
||||
|
||||
static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
@@ -2456,7 +2475,8 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
|
||||
return ResolveAs<SemIR::ImplWitnessAccess>(
|
||||
resolver,
|
||||
{.type_id = resolver.local_context().GetTypeIdForTypeConstant(type_id),
|
||||
{.type_id =
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(type_id),
|
||||
.witness_id = witness_id,
|
||||
.index = inst.index});
|
||||
}
|
||||
@@ -2477,7 +2497,8 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
|
||||
return ResolveAs<SemIR::IntValue>(
|
||||
resolver,
|
||||
{.type_id = resolver.local_context().GetTypeIdForTypeConstant(type_id),
|
||||
{.type_id =
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(type_id),
|
||||
.int_id = int_id});
|
||||
}
|
||||
|
||||
@@ -2511,8 +2532,8 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
return ResolveResult::Retry();
|
||||
}
|
||||
|
||||
auto namespace_type_id = resolver.local_context().GetSingletonType(
|
||||
SemIR::NamespaceType::SingletonInstId);
|
||||
auto namespace_type_id = GetSingletonType(
|
||||
resolver.local_context(), SemIR::NamespaceType::SingletonInstId);
|
||||
auto namespace_decl =
|
||||
SemIR::Namespace{.type_id = namespace_type_id,
|
||||
.name_scope_id = SemIR::NameScopeId::None,
|
||||
@@ -2543,7 +2564,8 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
}
|
||||
|
||||
auto pointee_type_id =
|
||||
resolver.local_context().GetTypeIdForTypeConstant(pointee_const_id);
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(
|
||||
pointee_const_id);
|
||||
return ResolveAs<SemIR::PointerType>(
|
||||
resolver, {.type_id = SemIR::TypeType::SingletonTypeId,
|
||||
.pointee_id = pointee_type_id});
|
||||
@@ -2562,11 +2584,13 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
}
|
||||
|
||||
auto complete_type_id =
|
||||
resolver.local_context().GetTypeIdForTypeConstant(complete_type_const_id);
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(
|
||||
complete_type_const_id);
|
||||
return ResolveAs<SemIR::RequireCompleteType>(
|
||||
resolver, {.type_id = resolver.local_context().GetSingletonType(
|
||||
SemIR::WitnessType::SingletonInstId),
|
||||
.complete_type_id = complete_type_id});
|
||||
resolver,
|
||||
{.type_id = GetSingletonType(resolver.local_context(),
|
||||
SemIR::WitnessType::SingletonInstId),
|
||||
.complete_type_id = complete_type_id});
|
||||
}
|
||||
|
||||
static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
@@ -2578,8 +2602,8 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
return ResolveResult::Retry();
|
||||
}
|
||||
|
||||
auto type_id =
|
||||
resolver.local_context().GetTypeIdForTypeConstant(type_const_id);
|
||||
auto type_id = resolver.local_context().types().GetTypeIdForTypeConstantId(
|
||||
type_const_id);
|
||||
auto specific_id =
|
||||
GetOrAddLocalSpecific(resolver, inst.specific_id, specific_data);
|
||||
return ResolveAs<SemIR::SpecificFunction>(
|
||||
@@ -2607,7 +2631,8 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
llvm::zip(orig_fields, field_const_ids)) {
|
||||
auto name_id = GetLocalNameId(resolver, orig_field.name_id);
|
||||
auto field_type_id =
|
||||
resolver.local_context().GetTypeIdForTypeConstant(field_const_id);
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(
|
||||
field_const_id);
|
||||
new_fields.push_back({.name_id = name_id, .type_id = field_type_id});
|
||||
}
|
||||
|
||||
@@ -2627,7 +2652,8 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
|
||||
return ResolveAs<SemIR::StructValue>(
|
||||
resolver,
|
||||
{.type_id = resolver.local_context().GetTypeIdForTypeConstant(type_id),
|
||||
{.type_id =
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(type_id),
|
||||
.elements_id =
|
||||
GetLocalCanonicalInstBlockId(resolver, inst.elements_id, elems)});
|
||||
}
|
||||
@@ -2651,11 +2677,12 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
elem_type_ids.reserve(orig_elem_type_ids.size());
|
||||
for (auto elem_const_id : elem_const_ids) {
|
||||
elem_type_ids.push_back(
|
||||
resolver.local_context().GetTypeIdForTypeConstant(elem_const_id));
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(
|
||||
elem_const_id));
|
||||
}
|
||||
|
||||
return ResolveResult::Done(resolver.local_types().GetConstantId(
|
||||
resolver.local_context().GetTupleType(elem_type_ids)));
|
||||
GetTupleType(resolver.local_context(), elem_type_ids)));
|
||||
}
|
||||
|
||||
static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
@@ -2668,7 +2695,8 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
|
||||
return ResolveAs<SemIR::TupleValue>(
|
||||
resolver,
|
||||
{.type_id = resolver.local_context().GetTypeIdForTypeConstant(type_id),
|
||||
{.type_id =
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(type_id),
|
||||
.elements_id =
|
||||
GetLocalCanonicalInstBlockId(resolver, inst.elements_id, elems)});
|
||||
}
|
||||
@@ -2687,9 +2715,11 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
|
||||
resolver,
|
||||
{.type_id = SemIR::TypeType::SingletonTypeId,
|
||||
.class_type_id =
|
||||
resolver.local_context().GetTypeIdForTypeConstant(class_const_id),
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(
|
||||
class_const_id),
|
||||
.element_type_id =
|
||||
resolver.local_context().GetTypeIdForTypeConstant(elem_const_id)});
|
||||
resolver.local_context().types().GetTypeIdForTypeConstantId(
|
||||
elem_const_id)});
|
||||
}
|
||||
|
||||
// Tries to resolve the InstId, returning a canonical constant when ready, or
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
#include "toolchain/check/context.h"
|
||||
#include "toolchain/check/eval.h"
|
||||
#include "toolchain/check/generic.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/sem_ir/ids.h"
|
||||
#include "toolchain/sem_ir/inst.h"
|
||||
#include "toolchain/sem_ir/typed_insts.h"
|
||||
@@ -34,7 +35,7 @@ auto BuildAssociatedEntity(Context& context, SemIR::InterfaceId interface_id,
|
||||
|
||||
// Name lookup for the declaration's name should name the associated entity,
|
||||
// not the declaration itself.
|
||||
auto type_id = context.GetAssociatedEntityType(self_type_id);
|
||||
auto type_id = GetAssociatedEntityType(context, self_type_id);
|
||||
return context.AddInst<SemIR::AssociatedEntity>(
|
||||
context.insts().GetLocId(decl_id),
|
||||
{.type_id = type_id, .index = index, .decl_id = decl_id});
|
||||
@@ -173,8 +174,9 @@ auto GetTypeForSpecificAssociatedEntity(Context& context, SemIRLoc loc,
|
||||
GetSelfFacet(context, interface_specific_id,
|
||||
context.functions().Get(fn->function_id).generic_id,
|
||||
self_type_id, self_witness_id);
|
||||
return context.GetFunctionTypeWithSelfType(
|
||||
context.types().GetInstId(interface_fn_type_id), self_facet_id);
|
||||
return GetFunctionTypeWithSelfType(
|
||||
context, context.types().GetInstId(interface_fn_type_id),
|
||||
self_facet_id);
|
||||
} else {
|
||||
CARBON_FATAL("Unexpected kind for associated constant {0}", decl);
|
||||
}
|
||||
|
||||
@@ -8,14 +8,15 @@
|
||||
#include "toolchain/check/context.h"
|
||||
#include "toolchain/check/convert.h"
|
||||
#include "toolchain/check/name_lookup.h"
|
||||
#include "toolchain/check/type.h"
|
||||
|
||||
namespace Carbon::Check {
|
||||
|
||||
auto MakeIntLiteral(Context& context, Parse::NodeId node_id, IntId int_id)
|
||||
-> SemIR::InstId {
|
||||
return context.AddInst<SemIR::IntValue>(
|
||||
node_id, {.type_id = context.GetSingletonType(
|
||||
SemIR::IntLiteralType::SingletonInstId),
|
||||
node_id, {.type_id = GetSingletonType(
|
||||
context, SemIR::IntLiteralType::SingletonInstId),
|
||||
.int_id = int_id});
|
||||
}
|
||||
|
||||
|
||||
@@ -14,6 +14,7 @@
|
||||
#include "toolchain/check/import_ref.h"
|
||||
#include "toolchain/check/interface.h"
|
||||
#include "toolchain/check/name_lookup.h"
|
||||
#include "toolchain/check/type.h"
|
||||
#include "toolchain/check/type_completion.h"
|
||||
#include "toolchain/diagnostics/diagnostic_emitter.h"
|
||||
#include "toolchain/sem_ir/function.h"
|
||||
@@ -194,13 +195,13 @@ static auto PerformImplLookup(
|
||||
return SemIR::ErrorInst::SingletonInstId;
|
||||
}
|
||||
|
||||
auto self_type_id = context.GetTypeIdForTypeConstant(type_const_id);
|
||||
auto self_type_id = context.types().GetTypeIdForTypeConstantId(type_const_id);
|
||||
auto witness_id =
|
||||
LookupImplWitness(context, loc_id, type_const_id,
|
||||
assoc_type.interface_type_id.AsConstantId());
|
||||
if (!witness_id.has_value()) {
|
||||
auto interface_type_id = context.GetInterfaceType(
|
||||
interface_type->interface_id, interface_type->specific_id);
|
||||
auto interface_type_id = GetInterfaceType(
|
||||
context, interface_type->interface_id, interface_type->specific_id);
|
||||
if (missing_impl_diagnoser) {
|
||||
// TODO: Pass in the expression whose type we are printing.
|
||||
CARBON_DIAGNOSTIC(MissingImplInMemberAccessNote, Note,
|
||||
@@ -286,7 +287,7 @@ static auto LookupMemberNameInScope(Context& context, SemIR::LocId loc_id,
|
||||
if (lookup_in_type_of_base) {
|
||||
SemIR::TypeId base_type_id = context.insts().Get(base_id).type_id();
|
||||
if (base_type_id != SemIR::TypeType::SingletonTypeId &&
|
||||
context.IsFacetType(base_type_id)) {
|
||||
context.types().IsFacetType(base_type_id)) {
|
||||
// Handles `T.F` when `T` is a non-type facet.
|
||||
auto base_as_type = ExprAsType(context, loc_id, base_id);
|
||||
|
||||
@@ -308,8 +309,8 @@ static auto LookupMemberNameInScope(Context& context, SemIR::LocId loc_id,
|
||||
// Get the witness that `T` implements `base_type_id`.
|
||||
if (base_interface == *assoc_interface) {
|
||||
witness_inst_id = context.GetOrAddInst<SemIR::FacetAccessWitness>(
|
||||
loc_id, {.type_id = context.GetSingletonType(
|
||||
SemIR::WitnessType::SingletonInstId),
|
||||
loc_id, {.type_id = GetSingletonType(
|
||||
context, SemIR::WitnessType::SingletonInstId),
|
||||
.facet_value_inst_id = base_id});
|
||||
// TODO: Result will eventually be a facet type witness instead of
|
||||
// an interface witness. Will need to use the index
|
||||
@@ -366,8 +367,8 @@ static auto PerformInstanceBinding(Context& context, SemIR::LocId loc_id,
|
||||
}
|
||||
|
||||
return context.GetOrAddInst<SemIR::BoundMethod>(
|
||||
loc_id, {.type_id = context.GetSingletonType(
|
||||
SemIR::BoundMethodType::SingletonInstId),
|
||||
loc_id, {.type_id = GetSingletonType(
|
||||
context, SemIR::BoundMethodType::SingletonInstId),
|
||||
.object_id = base_id,
|
||||
.function_decl_id = member_id});
|
||||
}
|
||||
@@ -508,7 +509,7 @@ auto PerformMemberAccess(Context& context, SemIR::LocId loc_id,
|
||||
// TODO: According to the design, this should be a "lookup in base" lookup,
|
||||
// not a "lookup in type of base" lookup, and the facet itself should have
|
||||
// member names that directly name members of the `impl`.
|
||||
if (context.IsFacetType(base_type_id)) {
|
||||
if (context.types().IsFacetType(base_type_id)) {
|
||||
return member_id;
|
||||
}
|
||||
|
||||
@@ -591,7 +592,7 @@ auto PerformTupleAccess(Context& context, SemIR::LocId loc_id,
|
||||
auto index_node_id = context.insts().GetLocId(index_inst_id);
|
||||
index_inst_id = ConvertToValueOfType(
|
||||
context, index_node_id, index_inst_id,
|
||||
context.GetSingletonType(SemIR::IntLiteralType::SingletonInstId));
|
||||
GetSingletonType(context, SemIR::IntLiteralType::SingletonInstId));
|
||||
auto index_const_id = context.constant_values().Get(index_inst_id);
|
||||
if (index_const_id == SemIR::ErrorInst::SingletonConstantId) {
|
||||
return SemIR::ErrorInst::SingletonInstId;
|
||||
|
||||
@@ -240,7 +240,8 @@ auto AppendLookupScopesForConstant(Context& context, SemIR::LocId loc_id,
|
||||
}
|
||||
if (auto base_as_class = base.TryAs<SemIR::ClassType>()) {
|
||||
RequireDefinedType(
|
||||
context, context.GetTypeIdForTypeConstant(base_const_id), loc_id, [&] {
|
||||
context, context.types().GetTypeIdForTypeConstantId(base_const_id),
|
||||
loc_id, [&] {
|
||||
CARBON_DIAGNOSTIC(QualifiedExprInIncompleteClassScope, Error,
|
||||
"member access into incomplete class {0}",
|
||||
InstIdAsType);
|
||||
@@ -254,7 +255,8 @@ auto AppendLookupScopesForConstant(Context& context, SemIR::LocId loc_id,
|
||||
}
|
||||
if (auto base_as_facet_type = base.TryAs<SemIR::FacetType>()) {
|
||||
RequireDefinedType(
|
||||
context, context.GetTypeIdForTypeConstant(base_const_id), loc_id, [&] {
|
||||
context, context.types().GetTypeIdForTypeConstantId(base_const_id),
|
||||
loc_id, [&] {
|
||||
CARBON_DIAGNOSTIC(QualifiedExprInUndefinedInterfaceScope, Error,
|
||||
"member access into undefined interface {0}",
|
||||
InstIdAsType);
|
||||
|
||||
@@ -13,6 +13,7 @@
|
||||
#include "toolchain/check/context.h"
|
||||
#include "toolchain/check/convert.h"
|
||||
#include "toolchain/check/subpattern.h"
|
||||
#include "toolchain/check/type.h"
|
||||
|
||||
namespace Carbon::Check {
|
||||
|
||||
@@ -252,7 +253,7 @@ auto MatchContext::EmitPatternMatch(Context& context,
|
||||
auto scrutinee_ref = context.insts().Get(scrutinee_ref_id);
|
||||
auto new_scrutinee = context.AddInst<SemIR::AddrOf>(
|
||||
context.insts().GetLocId(scrutinee_ref_id),
|
||||
{.type_id = context.GetPointerType(scrutinee_ref.type_id()),
|
||||
{.type_id = GetPointerType(context, scrutinee_ref.type_id()),
|
||||
.lvalue_id = scrutinee_ref_id});
|
||||
AddWork(
|
||||
{.pattern_id = addr_pattern.inner_id, .scrutinee_id = new_scrutinee});
|
||||
|
||||
@@ -172,7 +172,7 @@ static auto PopOperand(Context& context, Worklist& worklist, SemIR::IdKind kind,
|
||||
if (!type_id.has_value()) {
|
||||
return arg;
|
||||
}
|
||||
return context.GetTypeIdForTypeInst(worklist.Pop()).index;
|
||||
return context.types().GetTypeIdForTypeInstId(worklist.Pop()).index;
|
||||
}
|
||||
case SemIR::IdKind::For<SemIR::InstBlockId>: {
|
||||
return pop_block_id(SemIR::InstBlockId(arg)).index;
|
||||
@@ -183,9 +183,9 @@ static auto PopOperand(Context& context, Worklist& worklist, SemIR::IdKind kind,
|
||||
SemIR::CopyOnWriteStructTypeFieldsBlock new_fields(context.sem_ir(),
|
||||
old_fields_id);
|
||||
for (auto i : llvm::reverse(llvm::seq(old_fields.size()))) {
|
||||
new_fields.Set(
|
||||
i, {.name_id = old_fields[i].name_id,
|
||||
.type_id = context.GetTypeIdForTypeInst(worklist.Pop())});
|
||||
new_fields.Set(i, {.name_id = old_fields[i].name_id,
|
||||
.type_id = context.types().GetTypeIdForTypeInstId(
|
||||
worklist.Pop())});
|
||||
}
|
||||
return new_fields.GetCanonical().index;
|
||||
}
|
||||
@@ -195,7 +195,8 @@ static auto PopOperand(Context& context, Worklist& worklist, SemIR::IdKind kind,
|
||||
SemIR::CopyOnWriteTypeBlock new_type_block(context.sem_ir(),
|
||||
old_type_block_id);
|
||||
for (auto i : llvm::reverse(llvm::seq(size))) {
|
||||
new_type_block.Set(i, context.GetTypeIdForTypeInst(worklist.Pop()));
|
||||
new_type_block.Set(
|
||||
i, context.types().GetTypeIdForTypeInstId(worklist.Pop()));
|
||||
}
|
||||
return new_type_block.GetCanonical().index;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,116 @@
|
||||
// Part of the Carbon Language project, under the Apache License v2.0 with LLVM
|
||||
// Exceptions. See /LICENSE for license information.
|
||||
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
||||
|
||||
#include "toolchain/check/type.h"
|
||||
|
||||
#include "toolchain/check/eval.h"
|
||||
#include "toolchain/check/type_completion.h"
|
||||
|
||||
namespace Carbon::Check {
|
||||
|
||||
// Gets or forms a type_id for a type, given the instruction kind and arguments.
|
||||
template <typename InstT, typename... EachArgT>
|
||||
static auto GetTypeImpl(Context& context, EachArgT... each_arg)
|
||||
-> SemIR::TypeId {
|
||||
// TODO: Remove inst_id parameter from TryEvalInst.
|
||||
InstT inst = {SemIR::TypeType::SingletonTypeId, each_arg...};
|
||||
return context.types().GetTypeIdForTypeConstantId(
|
||||
TryEvalInst(context, SemIR::InstId::None, inst));
|
||||
}
|
||||
|
||||
auto FacetTypeFromInterface(Context& context, SemIR::InterfaceId interface_id,
|
||||
SemIR::SpecificId specific_id) -> SemIR::FacetType {
|
||||
SemIR::FacetTypeId facet_type_id = context.facet_types().Add(
|
||||
SemIR::FacetTypeInfo{.impls_constraints = {{interface_id, specific_id}},
|
||||
.other_requirements = false});
|
||||
return {.type_id = SemIR::TypeType::SingletonTypeId,
|
||||
.facet_type_id = facet_type_id};
|
||||
}
|
||||
|
||||
// Gets or forms a type_id for a type, given the instruction kind and arguments,
|
||||
// and completes the type. This should only be used when type completion cannot
|
||||
// fail.
|
||||
template <typename InstT, typename... EachArgT>
|
||||
static auto GetCompleteTypeImpl(Context& context, EachArgT... each_arg)
|
||||
-> SemIR::TypeId {
|
||||
auto type_id = GetTypeImpl<InstT>(context, each_arg...);
|
||||
CompleteTypeOrCheckFail(context, type_id);
|
||||
return type_id;
|
||||
}
|
||||
|
||||
auto GetStructType(Context& context, SemIR::StructTypeFieldsId fields_id)
|
||||
-> SemIR::TypeId {
|
||||
return GetTypeImpl<SemIR::StructType>(context, fields_id);
|
||||
}
|
||||
|
||||
auto GetTupleType(Context& context, llvm::ArrayRef<SemIR::TypeId> type_ids)
|
||||
-> SemIR::TypeId {
|
||||
return GetTypeImpl<SemIR::TupleType>(
|
||||
context, context.type_blocks().AddCanonical(type_ids));
|
||||
}
|
||||
|
||||
auto GetAssociatedEntityType(Context& context, SemIR::TypeId interface_type_id)
|
||||
-> SemIR::TypeId {
|
||||
return GetTypeImpl<SemIR::AssociatedEntityType>(context, interface_type_id);
|
||||
}
|
||||
|
||||
auto GetSingletonType(Context& context, SemIR::InstId singleton_id)
|
||||
-> SemIR::TypeId {
|
||||
CARBON_CHECK(SemIR::IsSingletonInstId(singleton_id));
|
||||
auto type_id = context.types().GetTypeIdForTypeInstId(singleton_id);
|
||||
// To keep client code simpler, complete builtin types before returning them.
|
||||
CompleteTypeOrCheckFail(context, type_id);
|
||||
return type_id;
|
||||
}
|
||||
|
||||
auto GetClassType(Context& context, SemIR::ClassId class_id,
|
||||
SemIR::SpecificId specific_id) -> SemIR::TypeId {
|
||||
return GetTypeImpl<SemIR::ClassType>(context, class_id, specific_id);
|
||||
}
|
||||
|
||||
auto GetFunctionType(Context& context, SemIR::FunctionId fn_id,
|
||||
SemIR::SpecificId specific_id) -> SemIR::TypeId {
|
||||
return GetCompleteTypeImpl<SemIR::FunctionType>(context, fn_id, specific_id);
|
||||
}
|
||||
|
||||
auto GetFunctionTypeWithSelfType(Context& context,
|
||||
SemIR::InstId interface_function_type_id,
|
||||
SemIR::InstId self_id) -> SemIR::TypeId {
|
||||
return GetCompleteTypeImpl<SemIR::FunctionTypeWithSelfType>(
|
||||
context, interface_function_type_id, self_id);
|
||||
}
|
||||
|
||||
auto GetGenericClassType(Context& context, SemIR::ClassId class_id,
|
||||
SemIR::SpecificId enclosing_specific_id)
|
||||
-> SemIR::TypeId {
|
||||
return GetCompleteTypeImpl<SemIR::GenericClassType>(context, class_id,
|
||||
enclosing_specific_id);
|
||||
}
|
||||
|
||||
auto GetGenericInterfaceType(Context& context, SemIR::InterfaceId interface_id,
|
||||
SemIR::SpecificId enclosing_specific_id)
|
||||
-> SemIR::TypeId {
|
||||
return GetCompleteTypeImpl<SemIR::GenericInterfaceType>(
|
||||
context, interface_id, enclosing_specific_id);
|
||||
}
|
||||
|
||||
auto GetInterfaceType(Context& context, SemIR::InterfaceId interface_id,
|
||||
SemIR::SpecificId specific_id) -> SemIR::TypeId {
|
||||
return GetTypeImpl<SemIR::FacetType>(
|
||||
context,
|
||||
FacetTypeFromInterface(context, interface_id, specific_id).facet_type_id);
|
||||
}
|
||||
|
||||
auto GetPointerType(Context& context, SemIR::TypeId pointee_type_id)
|
||||
-> SemIR::TypeId {
|
||||
return GetTypeImpl<SemIR::PointerType>(context, pointee_type_id);
|
||||
}
|
||||
|
||||
auto GetUnboundElementType(Context& context, SemIR::TypeId class_type_id,
|
||||
SemIR::TypeId element_type_id) -> SemIR::TypeId {
|
||||
return GetTypeImpl<SemIR::UnboundElementType>(context, class_type_id,
|
||||
element_type_id);
|
||||
}
|
||||
|
||||
} // namespace Carbon::Check
|
||||
@@ -0,0 +1,83 @@
|
||||
// Part of the Carbon Language project, under the Apache License v2.0 with LLVM
|
||||
// Exceptions. See /LICENSE for license information.
|
||||
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
||||
|
||||
#ifndef CARBON_TOOLCHAIN_CHECK_TYPE_H_
|
||||
#define CARBON_TOOLCHAIN_CHECK_TYPE_H_
|
||||
|
||||
#include "llvm/ADT/ArrayRef.h"
|
||||
#include "toolchain/check/context.h"
|
||||
#include "toolchain/sem_ir/ids.h"
|
||||
|
||||
namespace Carbon::Check {
|
||||
|
||||
// Create a FacetType typed instruction object consisting of a single
|
||||
// interface.
|
||||
auto FacetTypeFromInterface(Context& context, SemIR::InterfaceId interface_id,
|
||||
SemIR::SpecificId specific_id) -> SemIR::FacetType;
|
||||
|
||||
// Gets the type to use for an unbound associated entity declared in this
|
||||
// interface. For example, this is the type of `I.T` after
|
||||
// `interface I { let T:! type; }`. The name of the interface is used for
|
||||
// diagnostics.
|
||||
// TODO: Should we use a different type for each such entity, or the same type
|
||||
// for all associated entities?
|
||||
auto GetAssociatedEntityType(Context& context, SemIR::TypeId interface_type_id)
|
||||
-> SemIR::TypeId;
|
||||
|
||||
// Gets a singleton type. The returned type will be complete. Requires that
|
||||
// `singleton_id` is already validated to be a singleton.
|
||||
auto GetSingletonType(Context& context, SemIR::InstId singleton_id)
|
||||
-> SemIR::TypeId;
|
||||
|
||||
// Gets a class type.
|
||||
auto GetClassType(Context& context, SemIR::ClassId class_id,
|
||||
SemIR::SpecificId specific_id) -> SemIR::TypeId;
|
||||
|
||||
// Gets a function type. The returned type will be complete.
|
||||
auto GetFunctionType(Context& context, SemIR::FunctionId fn_id,
|
||||
SemIR::SpecificId specific_id) -> SemIR::TypeId;
|
||||
|
||||
// Gets the type of an associated function with the `Self` parameter bound to
|
||||
// a particular value. The returned type will be complete.
|
||||
auto GetFunctionTypeWithSelfType(Context& context,
|
||||
SemIR::InstId interface_function_type_id,
|
||||
SemIR::InstId self_id) -> SemIR::TypeId;
|
||||
|
||||
// Gets a generic class type, which is the type of a name of a generic class,
|
||||
// such as the type of `Vector` given `class Vector(T:! type)`. The returned
|
||||
// type will be complete.
|
||||
auto GetGenericClassType(Context& context, SemIR::ClassId class_id,
|
||||
SemIR::SpecificId enclosing_specific_id)
|
||||
-> SemIR::TypeId;
|
||||
|
||||
// Gets a generic interface type, which is the type of a name of a generic
|
||||
// interface, such as the type of `AddWith` given
|
||||
// `interface AddWith(T:! type)`. The returned type will be complete.
|
||||
auto GetGenericInterfaceType(Context& context, SemIR::InterfaceId interface_id,
|
||||
SemIR::SpecificId enclosing_specific_id)
|
||||
-> SemIR::TypeId;
|
||||
|
||||
// Gets the facet type corresponding to a particular interface.
|
||||
auto GetInterfaceType(Context& context, SemIR::InterfaceId interface_id,
|
||||
SemIR::SpecificId specific_id) -> SemIR::TypeId;
|
||||
|
||||
// Returns a pointer type whose pointee type is `pointee_type_id`.
|
||||
auto GetPointerType(Context& context, SemIR::TypeId pointee_type_id)
|
||||
-> SemIR::TypeId;
|
||||
|
||||
// Returns a struct type with the given fields.
|
||||
auto GetStructType(Context& context, SemIR::StructTypeFieldsId fields_id)
|
||||
-> SemIR::TypeId;
|
||||
|
||||
// Returns a tuple type with the given element types.
|
||||
auto GetTupleType(Context& context, llvm::ArrayRef<SemIR::TypeId> type_ids)
|
||||
-> SemIR::TypeId;
|
||||
|
||||
// Returns an unbound element type.
|
||||
auto GetUnboundElementType(Context& context, SemIR::TypeId class_type_id,
|
||||
SemIR::TypeId element_type_id) -> SemIR::TypeId;
|
||||
|
||||
} // namespace Carbon::Check
|
||||
|
||||
#endif // CARBON_TOOLCHAIN_CHECK_TYPE_H_
|
||||
@@ -7,6 +7,7 @@
|
||||
#include "llvm/ADT/SmallVector.h"
|
||||
#include "toolchain/base/kind_switch.h"
|
||||
#include "toolchain/check/generic.h"
|
||||
#include "toolchain/check/type.h"
|
||||
|
||||
namespace Carbon::Check {
|
||||
|
||||
@@ -290,7 +291,8 @@ auto TypeCompleter::AddNestedIncompleteTypes(SemIR::Inst type_inst) -> bool {
|
||||
}
|
||||
|
||||
auto TypeCompleter::MakeEmptyValueRepr() const -> SemIR::ValueRepr {
|
||||
return {.kind = SemIR::ValueRepr::None, .type_id = context_.GetTupleType({})};
|
||||
return {.kind = SemIR::ValueRepr::None,
|
||||
.type_id = GetTupleType(context_, {})};
|
||||
}
|
||||
|
||||
auto TypeCompleter::MakeCopyValueRepr(
|
||||
@@ -307,7 +309,7 @@ auto TypeCompleter::MakePointerValueRepr(
|
||||
// TODO: Should we add `const` qualification to `pointee_id`?
|
||||
return {.kind = SemIR::ValueRepr::Pointer,
|
||||
.aggregate_kind = aggregate_kind,
|
||||
.type_id = context_.GetPointerType(pointee_id)};
|
||||
.type_id = GetPointerType(context_, pointee_id)};
|
||||
}
|
||||
|
||||
auto TypeCompleter::GetNestedValueRepr(SemIR::TypeId nested_type_id) const
|
||||
@@ -375,8 +377,8 @@ auto TypeCompleter::BuildValueReprForInst(SemIR::TypeId type_id,
|
||||
auto value_rep =
|
||||
same_as_object_rep
|
||||
? type_id
|
||||
: context_.GetStructType(
|
||||
context_.struct_type_fields().AddCanonical(value_rep_fields));
|
||||
: GetStructType(context_, context_.struct_type_fields().AddCanonical(
|
||||
value_rep_fields));
|
||||
return BuildStructOrTupleValueRepr(fields.size(), value_rep,
|
||||
same_as_object_rep);
|
||||
}
|
||||
@@ -405,7 +407,7 @@ auto TypeCompleter::BuildValueReprForInst(SemIR::TypeId type_id,
|
||||
}
|
||||
|
||||
auto value_rep =
|
||||
same_as_object_rep ? type_id : context_.GetTupleType(value_rep_elements);
|
||||
same_as_object_rep ? type_id : GetTupleType(context_, value_rep_elements);
|
||||
return BuildStructOrTupleValueRepr(elements.size(), value_rep,
|
||||
same_as_object_rep);
|
||||
}
|
||||
@@ -488,10 +490,10 @@ auto RequireCompleteType(Context& context, SemIR::TypeId type_id,
|
||||
if (type_id.AsConstantId().is_symbolic()) {
|
||||
// TODO: Deduplicate these.
|
||||
context.AddInstInNoBlock(SemIR::LocIdAndInst(
|
||||
loc_id,
|
||||
SemIR::RequireCompleteType{.type_id = context.GetSingletonType(
|
||||
SemIR::WitnessType::SingletonInstId),
|
||||
.complete_type_id = type_id}));
|
||||
loc_id, SemIR::RequireCompleteType{
|
||||
.type_id = GetSingletonType(
|
||||
context, SemIR::WitnessType::SingletonInstId),
|
||||
.complete_type_id = type_id}));
|
||||
}
|
||||
|
||||
return true;
|
||||
|
||||
@@ -298,11 +298,11 @@ If the resulting SemIR needs a new instruction:
|
||||
constructed as a special-case in
|
||||
[`File` construction](/toolchain/sem_ir/file.cpp). To get a type id for
|
||||
one of these builtin types, use something like
|
||||
`context.GetSingletonType(SemIR::WitnessType::SingletonInstId)`, as in:
|
||||
`GetSingletonType(context,SemIR::WitnessType::SingletonInstId)`, as in:
|
||||
|
||||
```
|
||||
SemIR::TypeId witness_type_id =
|
||||
context.GetSingletonType(SemIR::WitnessType::SingletonInstId);
|
||||
GetSingletonType(context,SemIR::WitnessType::SingletonInstId);
|
||||
SemIR::InstId inst_id = context.AddInst<SemIR::NewInstKindName>(
|
||||
node_id, {.type_id = witness_type_id, ...});
|
||||
```
|
||||
|
||||
@@ -8,6 +8,26 @@
|
||||
|
||||
namespace Carbon::SemIR {
|
||||
|
||||
auto TypeStore::GetTypeIdForTypeConstantId(SemIR::ConstantId constant_id) const
|
||||
-> SemIR::TypeId {
|
||||
CARBON_CHECK(constant_id.is_constant(),
|
||||
"Canonicalizing non-constant type: {0}", constant_id);
|
||||
auto type_id = file_->insts()
|
||||
.Get(file_->constant_values().GetInstId(constant_id))
|
||||
.type_id();
|
||||
CARBON_CHECK(type_id == SemIR::TypeType::SingletonTypeId ||
|
||||
constant_id == SemIR::ErrorInst::SingletonConstantId,
|
||||
"Forming type ID for non-type constant of type {0}",
|
||||
GetAsInst(type_id));
|
||||
|
||||
return SemIR::TypeId::ForTypeConstant(constant_id);
|
||||
}
|
||||
|
||||
auto TypeStore::GetTypeIdForTypeInstId(SemIR::InstId inst_id) const
|
||||
-> SemIR::TypeId {
|
||||
return GetTypeIdForTypeConstantId(file_->constant_values().Get(inst_id));
|
||||
}
|
||||
|
||||
auto TypeStore::GetInstId(TypeId type_id) const -> InstId {
|
||||
return file_->constant_values().GetInstId(GetConstantId(type_id));
|
||||
}
|
||||
|
||||
@@ -33,6 +33,25 @@ class TypeStore : public Yaml::Printable<TypeStore> {
|
||||
return type_id.AsConstantId();
|
||||
}
|
||||
|
||||
// Returns the type ID for a constant that is a type value, i.e. it is a value
|
||||
// of type `TypeType`.
|
||||
//
|
||||
// Facet values are of the same typishness as types, but are not themselves
|
||||
// types, so they can not be passed here. They should be converted to a type
|
||||
// through an `as type` conversion, that is, to a value of type `TypeType`.
|
||||
auto GetTypeIdForTypeConstantId(SemIR::ConstantId constant_id) const
|
||||
-> SemIR::TypeId;
|
||||
|
||||
// Returns the type ID for an instruction whose constant value is a type
|
||||
// value, i.e. it is a value of type `TypeType`.
|
||||
//
|
||||
// Instructions whose values are facet values (see `FacetValue`) produce a
|
||||
// value of the same typishness as types, but which are themselves not types,
|
||||
// so they can not be passed here. They should be converted to a type through
|
||||
// an `as type` conversion, such as to a `FacetAccessType` instruction whose
|
||||
// value is of type `TypeType`.
|
||||
auto GetTypeIdForTypeInstId(SemIR::InstId inst_id) const -> SemIR::TypeId;
|
||||
|
||||
// Returns the ID of the instruction used to define the specified type.
|
||||
auto GetInstId(TypeId type_id) const -> InstId;
|
||||
|
||||
@@ -113,6 +132,12 @@ class TypeStore : public Yaml::Printable<TypeStore> {
|
||||
// non-constant width and for IntLiteral.
|
||||
auto GetIntTypeInfo(TypeId int_type_id) const -> IntTypeInfo;
|
||||
|
||||
// Returns whether `type_id` represents a facet type.
|
||||
auto IsFacetType(SemIR::TypeId type_id) const -> bool {
|
||||
return type_id == SemIR::TypeType::SingletonTypeId ||
|
||||
Is<SemIR::FacetType>(type_id);
|
||||
}
|
||||
|
||||
// Returns a list of types that were completed in this file, in the order in
|
||||
// which they were completed. Earlier types in this list cannot contain
|
||||
// instances of later types.
|
||||
|
||||
Reference in New Issue
Block a user