Add an instruction to represent a use of a dependent value from a generic instance. (#4122)

We can't use the instruction from the generic directly, because it
doesn't have the right constant value. Instead add an instruction that
models the transition from the constant value in the generic to the
constant value in the generic instance.

Also start associating the self generic instance with unqualified
lookups that find results in an enclosing generic, so that we track the
information necessary to create the new instruction.

---------

Co-authored-by: Jon Ross-Perkins <jperkins@google.com>
This commit is contained in:
Richard Smith
2024-07-12 14:59:01 +00:00
committed by GitHub
co-authored by Jon Ross-Perkins
parent 6d2d1cf7ca
commit 50d56aa7c9
30 changed files with 259 additions and 144 deletions
+15 -4
View File
@@ -14,19 +14,28 @@ auto ScopeStack::VerifyOnFinish() -> void {
}
auto ScopeStack::Push(SemIR::InstId scope_inst_id, SemIR::NameScopeId scope_id,
SemIR::GenericInstanceId instance_id,
bool lexical_lookup_has_load_error) -> void {
compile_time_binding_stack_.PushArray();
scope_stack_.push_back(
{.index = next_scope_index_,
.scope_inst_id = scope_inst_id,
.scope_id = scope_id,
.instance_id = instance_id,
.next_compile_time_bind_index = SemIR::CompileTimeBindIndex(
compile_time_binding_stack_.all_values_size()),
.lexical_lookup_has_load_error =
LexicalLookupHasLoadError() || lexical_lookup_has_load_error});
if (scope_id.is_valid()) {
non_lexical_scope_stack_.push_back(
{.scope_index = next_scope_index_, .name_scope_id = scope_id});
non_lexical_scope_stack_.push_back({.scope_index = next_scope_index_,
.name_scope_id = scope_id,
.instance_id = instance_id});
} else {
// For lexical lookups, unqualified lookup doesn't know how to find the
// associated generic instance, so if we start adding lexical scopes with
// generic instances, we'll need to somehow track them in lookup.
CARBON_CHECK(!instance_id.is_valid())
<< "Lexical scope should not have an associated generic instance.";
}
// TODO: Handle this case more gracefully.
@@ -207,8 +216,10 @@ auto ScopeStack::Restore(SuspendedScope scope) -> void {
<< scope.entry.next_compile_time_bind_index.index;
if (scope.entry.scope_id.is_valid()) {
non_lexical_scope_stack_.push_back({.scope_index = scope.entry.index,
.name_scope_id = scope.entry.scope_id});
non_lexical_scope_stack_.push_back(
{.scope_index = scope.entry.index,
.name_scope_id = scope.entry.scope_id,
.instance_id = scope.entry.instance_id});
}
scope_stack_.push_back(std::move(scope.entry));
}