Repository navigation
A qualified path's first segment is a namespace root: reference-derived edges no longer bind it to a same-named declaration - #12190
Merged
Conversation
…erived producer no longer resolves it to a same-named declaration ExprVarClassification classify treated a dotted chain's head as a namespace segment only when no declaration anywhere shared its spelling, and reference_resolution_facts runs with no declaration index, so the head of every v2.std.* path fell to the free-reference default and resolved UniqueBare to test.claim.secret_rotation_witness fn v2(). A head whose chain names a declared module is now QualifiedChainHead; binders still outrank it and value chains keep their edges. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
This was referenced Sep 24, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
A qualified path's first segment is a namespace root, never a bare reference
Defect.
test.claim.secret_rotation_witnessdeclaresfn v2(). Every import-free production module reading av2.std.*path (among themsrc/v2/std/artifact,src/v2/std/groundingandsrc/v2/std/cross_tree/resolution) got a reference-derived dependency edge into that test module. The edge came fromdependency_resolution_facts_live, via the hostreference_resolution_facts. Found by the Pkg7e plan (v2.workflow.emitted_crate_workspace, on its own branch): its two-closure join refused with ClosuresDisagree. The live DAG ofv2.compiler.compilehad 214 modules against the seed emission's 190, and the extra 24 included that test claim.Earliest unjustified link (DESIGN §6b).
v1_compiler.cli_runExprVarClassification::classifycounted a dotted chain's head as a namespace segment only when no declaration anywhere shared its spelling.reference_resolution_factsruns with no declaration index (decl_index: None), so that arm could never fire. Every chain head therefore fell to the free-reference default, went intobare, and resolved UniqueBare to the homonym.longest_declared_module_prefix. The head's role was a fact the producer held and did not consult.Repair, at that link.
ExprVarClassificationgains the declared module set (module_names). Both production callers already hold it; the binder fixtures passNoneand keep their behaviour.QualifiedChainHead, the member it always belonged to, so no bare edge is emitted..field, keeps its edge.Evidence, by execution.
test.claim.namespace_root_reference_edge_witnessruns the real producer overfixtures/namespace_root_homonym. That pool is outside the corpus roots, so the homonym never enters the live pool. In it,nsroot_decl.homonymdeclaresfn nsroot()beside thensroot.pkg.*modules.a_qualified_path_head_never_resolves_to_a_same_named_declaration: FAIL on the unrepaired binary, PASS after.the_qualified_target_and_a_value_chain_keep_their_edges: PASS on both. The qualified edge and a value-chain edge survive.emitted_compiler_closure_module_dagnow derives 190 modules (it was 214) and no longer containstest.claim.secret_rotation_witness; the seed emits 190. That is count equality only. The identity-grain join is the Pkg7e plan'sClosuresDisagreecheck, which runs when 7e is un-held on top of this.module_graph_edge_source_witness(5/5),emitted_closure_crate_partition_test(4/4),bare_name_ambiguity_wall_witness_test(8/8).gunbc.recurring_failure_modea_namespace_root_segment_resolves_as_a_bare_reference, with its ceiling and the namespace-cut terminal step as the next-rung trigger.Consistency with the namespace-cut plan.
docs/plans/namespace-cut-replacement-plan.mdrepointsdependency_resolution_facts_liveto the reference-derived producer and makes parse-then-derive the terminal mechanism. This keeps that producer honest in the meantime, and it adds no second edge producer. No open PR touchesentry_resolve.rsorv2.lens.module_graph.v1 admission. This changes hand host Rust (
cli_run.rs,cli_run/entry_resolve.rs). It is admitted as v2 self-host work undergunbc.v1_maintenance_standingv1_seed_standing: the dependency facts decide the emitted compiler's crate partition. Receipt:ref_field_chain_head) and +2 fields on an existing struct.classifyandcollect_node_refs_innerare modified, not added.pub modis added.🤖 Generated with Claude Code