mirror of
https://github.com/carbon-language/carbon-lang.git
synced 2026-10-04 15:41:04 +01:00
Refactor handling of cross-package imports. (#3783)
This revamps the support for cross-package imports, making them look more like a namespace. The planned model is mentioned on [#toolchain](https://discord.com/channels/655572317891461132/655578254970716160/1217586076022210670). This does not implement name lookup into the new namespace structure. A few key changes in this PR (it's a little sprawling) are: - Moves logic for adding package imports from context.* to import.* - Remove SemIR::Import, which was the prior model. This is instead now a SemIR::Namespace with the NameScope getting a new import_ir_scopes field. - Allow SemIR::Namespace to use Parse::ImportDirectiveId in addition to the prior Parse::NamespaceId - The import_ir_scopes field includes a NameScopeId so that as we traverse to child namespaces, we can directly perform name lookup in the other IR. - is_closed_import now tracks whether a namespace comes from a different package. This has a diagnostic implemented in decl_name_stack.
This commit is contained in:
@@ -133,14 +133,14 @@ auto Context::ReplaceInstBeforeConstantUse(
|
||||
constant_values().Set(inst_id, const_id);
|
||||
}
|
||||
|
||||
auto Context::DiagnoseDuplicateName(SemIR::InstId dup_def_id,
|
||||
SemIR::InstId prev_def_id) -> void {
|
||||
auto Context::DiagnoseDuplicateName(SemIRLocation dup_def,
|
||||
SemIRLocation prev_def) -> void {
|
||||
CARBON_DIAGNOSTIC(NameDeclDuplicate, Error,
|
||||
"Duplicate name being declared in the same scope.");
|
||||
CARBON_DIAGNOSTIC(NameDeclPrevious, Note,
|
||||
"Name is previously declared here.");
|
||||
emitter_->Build(dup_def_id, NameDeclDuplicate)
|
||||
.Note(prev_def_id, NameDeclPrevious)
|
||||
emitter_->Build(dup_def, NameDeclDuplicate)
|
||||
.Note(prev_def, NameDeclPrevious)
|
||||
.Emit();
|
||||
}
|
||||
|
||||
@@ -182,43 +182,6 @@ auto Context::NoteUndefinedInterface(SemIR::InterfaceId interface_id,
|
||||
}
|
||||
}
|
||||
|
||||
auto Context::AddPackageImports(Parse::NodeId import_node,
|
||||
IdentifierId package_id,
|
||||
llvm::ArrayRef<const SemIR::File*> sem_irs,
|
||||
bool has_load_error) -> void {
|
||||
CARBON_CHECK(has_load_error || !sem_irs.empty())
|
||||
<< "There should be either a load error or at least one IR.";
|
||||
|
||||
auto name_id = SemIR::NameId::ForIdentifier(package_id);
|
||||
|
||||
SemIR::ImportIRId first_id(import_irs().size());
|
||||
for (const auto* sem_ir : sem_irs) {
|
||||
import_irs().Add(sem_ir);
|
||||
}
|
||||
if (has_load_error) {
|
||||
import_irs().Add(nullptr);
|
||||
}
|
||||
SemIR::ImportIRId last_id(import_irs().size() - 1);
|
||||
|
||||
auto type_id = GetBuiltinType(SemIR::BuiltinKind::NamespaceType);
|
||||
auto inst_id =
|
||||
AddInst({import_node, SemIR::Import{.type_id = type_id,
|
||||
.first_import_ir_id = first_id,
|
||||
.last_import_ir_id = last_id}});
|
||||
|
||||
// Add the import to lookup. Should always succeed because imports will be
|
||||
// uniquely named.
|
||||
AddNameToLookup(name_id, inst_id);
|
||||
// Add a name for formatted output. This isn't used in name lookup in order
|
||||
// to reduce indirection, but it's separate from the Import because it
|
||||
// otherwise fits in an Inst.
|
||||
auto bind_name_id = bind_names().Add(
|
||||
{.name_id = name_id, .enclosing_scope_id = SemIR::NameScopeId::Package});
|
||||
AddInst({import_node, SemIR::BindName{.type_id = type_id,
|
||||
.bind_name_id = bind_name_id,
|
||||
.value_id = inst_id}});
|
||||
}
|
||||
|
||||
auto Context::AddNameToLookup(SemIR::NameId name_id, SemIR::InstId target_id)
|
||||
-> void {
|
||||
if (auto existing = scope_stack().LookupOrAddName(name_id, target_id);
|
||||
@@ -837,7 +800,6 @@ class TypeCompleter {
|
||||
case SemIR::FieldDecl::Kind:
|
||||
case SemIR::FunctionDecl::Kind:
|
||||
case SemIR::ImplDecl::Kind:
|
||||
case SemIR::Import::Kind:
|
||||
case SemIR::ImportRefUnused::Kind:
|
||||
case SemIR::InitializeFrom::Kind:
|
||||
case SemIR::InterfaceDecl::Kind:
|
||||
|
||||
Reference in New Issue
Block a user