1515#include " toolchain/base/shared_value_stores.h"
1616#include " toolchain/check/context.h"
1717#include " toolchain/check/eval.h"
18+ #include " toolchain/check/facet_type.h"
1819#include " toolchain/check/generic.h"
1920#include " toolchain/check/import.h"
2021#include " toolchain/check/inst.h"
@@ -494,7 +495,7 @@ static auto SetIndirectConstantValues(
494495// Adds an import_ref instruction for an instruction that we have already loaded
495496// from an imported IR, with a known constant value. This is useful when the
496497// instruction has a symbolic constant value, in order to produce an instruction
497- // that hold that symbolic constant.
498+ // that holds that symbolic constant.
498499static auto AddLoadedImportRef (ImportContext& context,
499500 SemIR::TypeId local_type_id,
500501 SemIR::InstId import_inst_id,
@@ -869,8 +870,14 @@ static auto GetLocalConstantId(ImportRefResolver& resolver,
869870 // declaration.
870871 return GetLocalConstantId (resolver, import_decl_inst_id);
871872 }
873+ if (import_decl_inst.Is <SemIR::RequireImplsDecl>()) {
874+ // For an impl declaration, the imported entity can be found via the
875+ // declaration.
876+ return GetLocalConstantId (resolver, import_decl_inst_id);
877+ }
872878 // For all other kinds of declaration, the imported entity can be found via
873879 // the type of the declaration.
880+ CARBON_CHECK (import_decl_inst.type_id ().has_value ());
874881 return GetLocalConstantId (resolver, import_decl_inst.type_id ());
875882}
876883
@@ -904,6 +911,11 @@ static auto GetLocalGenericId(ImportContext& context,
904911 case CARBON_KIND (SemIR::ImplDecl impl_decl): {
905912 return context.local_impls ().Get (impl_decl.impl_id ).generic_id ;
906913 }
914+ case CARBON_KIND (SemIR::RequireImplsDecl require_decl): {
915+ return context.local_require_impls ()
916+ .Get (require_decl.require_impls_id )
917+ .generic_id ;
918+ }
907919 default : {
908920 CARBON_FATAL (" Unexpected inst for generic declaration: {0}" , inst);
909921 }
@@ -2562,6 +2574,13 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
25622574 resolver, import_impl.constraint_id , constraint_const_id);
25632575 new_impl.interface = GetLocalSpecificInterface (
25642576 resolver, import_impl.interface , specific_interface_data);
2577+ // Create a local IdentifiedFacetType for the imported facet type, since impl
2578+ // declarations always identify the facet type.
2579+ if (auto facet_type = resolver.local_insts ().TryGetAs <SemIR::FacetType>(
2580+ resolver.local_constant_values ().GetInstId (constraint_const_id))) {
2581+ RequireIdentifiedFacetType (resolver.local_context (), SemIR::LocId::None,
2582+ *facet_type, nullptr );
2583+ }
25652584 if (import_impl.is_complete ()) {
25662585 AddImplDefinition (resolver, import_impl, new_impl);
25672586 }
@@ -2579,10 +2598,45 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
25792598}
25802599
25812600static auto TryResolveTypedInst (ImportRefResolver& resolver,
2582- SemIR::RequireImplsDecl inst) -> ResolveResult {
2601+ SemIR::RequireImplsDecl inst,
2602+ SemIR::ConstantId require_decl_const_id)
2603+ -> ResolveResult {
25832604 const auto & import_require =
25842605 resolver.import_require_impls ().Get (inst.require_impls_id );
25852606
2607+ auto require_decl_id = SemIR::InstId::None;
2608+ auto require_impls_id = SemIR::RequireImplsId::None;
2609+ if (!require_decl_const_id.has_value ()) {
2610+ // Phase one: Make the decl and structure with placeholder values to be
2611+ // filled in. Begin the generic so instructions can be attached to it.
2612+ SemIR::RequireImplsDecl require_decl = {
2613+ .require_impls_id = SemIR::RequireImplsId::None,
2614+ .decl_block_id = SemIR::InstBlockId::Empty};
2615+ auto require_decl_id = AddPlaceholderImportedInst (
2616+ resolver, import_require.decl_id , require_decl);
2617+ require_impls_id = resolver.local_require_impls ().Add (
2618+ {.self_id = SemIR::TypeInstId::None,
2619+ .facet_type_inst_id = SemIR::TypeInstId::None,
2620+ .facet_type_id = SemIR::FacetTypeId::None,
2621+ .decl_id = require_decl_id,
2622+ .parent_scope_id = SemIR::NameScopeId::None,
2623+ .generic_id = MakeIncompleteGeneric (resolver, require_decl_id,
2624+ import_require.generic_id )});
2625+
2626+ // Write the RequireImplsId into the RequireImplsDecl.
2627+ require_decl.require_impls_id = require_impls_id;
2628+ require_decl_const_id =
2629+ ReplacePlaceholderImportedInst (resolver, require_decl_id, require_decl);
2630+ } else {
2631+ // Phase two: Get the `require_decl_id` and `require_impls_id` from the
2632+ // RequireImplsDecl constructed in phase one.
2633+ require_decl_id =
2634+ resolver.local_constant_values ().GetInstId (require_decl_const_id);
2635+ require_impls_id = resolver.local_insts ()
2636+ .GetAs <SemIR::RequireImplsDecl>(require_decl_id)
2637+ .require_impls_id ;
2638+ }
2639+
25862640 // Load dependent constants.
25872641 auto parent_scope_id =
25882642 GetLocalNameScopeId (resolver, import_require.parent_scope_id );
@@ -2592,29 +2646,9 @@ static auto TryResolveTypedInst(ImportRefResolver& resolver,
25922646 GetLocalConstantId (resolver, import_require.facet_type_inst_id );
25932647
25942648 if (resolver.HasNewWork ()) {
2595- return ResolveResult::Retry ();
2649+ return ResolveResult::Retry (require_decl_const_id, require_decl_id );
25962650 }
25972651
2598- // Make the decl and structure with placeholder values to be filled in.
2599- SemIR::RequireImplsDecl require_decl = {
2600- .require_impls_id = SemIR::RequireImplsId::None,
2601- .decl_block_id = SemIR::InstBlockId::Empty};
2602- auto require_decl_id = AddPlaceholderImportedInst (
2603- resolver, import_require.decl_id , require_decl);
2604- auto require_impls_id = resolver.local_require_impls ().Add (
2605- {.self_id = SemIR::TypeInstId::None,
2606- .facet_type_inst_id = SemIR::TypeInstId::None,
2607- .facet_type_id = SemIR::FacetTypeId::None,
2608- .decl_id = require_decl_id,
2609- .parent_scope_id = SemIR::NameScopeId::None,
2610- .generic_id = MakeIncompleteGeneric (resolver, require_decl_id,
2611- import_require.generic_id )});
2612-
2613- // Write the RequireImplsId into the RequireImplsDecl.
2614- require_decl.require_impls_id = require_impls_id;
2615- auto require_decl_const_id =
2616- ReplacePlaceholderImportedInst (resolver, require_decl_id, require_decl);
2617-
26182652 // Fill in the RequireImpls structure.
26192653 auto & new_require = resolver.local_require_impls ().Get (require_impls_id);
26202654 new_require.self_id = AddLoadedImportRefForType (
@@ -3604,6 +3638,9 @@ static auto TryResolveInstCanonical(ImportRefResolver& resolver,
36043638 case CARBON_KIND (SemIR::NamedConstraintDecl inst): {
36053639 return TryResolveTypedInst (resolver, inst, const_id);
36063640 }
3641+ case CARBON_KIND (SemIR::RequireImplsDecl inst): {
3642+ return TryResolveTypedInst (resolver, inst, const_id);
3643+ }
36073644 default :
36083645 break ;
36093646 }
@@ -3774,9 +3811,6 @@ static auto TryResolveInstCanonical(ImportRefResolver& resolver,
37743811 case CARBON_KIND (SemIR::RequireCompleteType inst): {
37753812 return TryResolveTypedInst (resolver, inst);
37763813 }
3777- case CARBON_KIND (SemIR::RequireImplsDecl inst): {
3778- return TryResolveTypedInst (resolver, inst);
3779- }
37803814 case CARBON_KIND (SemIR::RequireSpecificDefinition inst): {
37813815 return TryResolveTypedInst (resolver, inst);
37823816 }
0 commit comments