Skip to content

fix(semantic): don't ICE when an impl provides an associated item of the wrong kind#10206

Open
orizi wants to merge 1 commit into
mainfrom
orizi/07-17-fix_semantic_don_t_ice_when_an_impl_provides_an_associated_item_of_the_wrong_kind
Open

fix(semantic): don't ICE when an impl provides an associated item of the wrong kind#10206
orizi wants to merge 1 commit into
mainfrom
orizi/07-17-fix_semantic_don_t_ice_when_an_impl_provides_an_associated_item_of_the_wrong_kind

Conversation

@orizi

@orizi orizi commented Jul 17, 2026

Copy link
Copy Markdown
Collaborator

Summary

When an impl provides an associated item with the wrong kind (e.g., a const where a type is expected, or a type where an impl is expected), the compiler previously panicked via extract_matches! instead of emitting a proper diagnostic. This PR replaces those panicking extract_matches! calls with try_extract_matches! in impl_type_by_trait_type, impl_constant_by_trait_constant, and impl_impl_by_trait_impl, so that a mismatched-kind item is treated as "not found" and a graceful skip_diagnostic error is returned instead.

A new test case is added covering cross-kind collisions where MyImpl provides a const AsType, type AsConst, and type AsImpl against a trait expecting a type AsType, const AsConst, and impl AsImpl, verifying that appropriate E2014 diagnostics are emitted for each mismatched item.


Type of change

Please check one:

  • Bug fix (fixes incorrect behavior)
  • New feature
  • Performance improvement
  • Documentation change with concrete technical impact
  • Style, wording, formatting, or typo-only change

Why is this change needed?

When an impl supplies an associated item under the correct name but the wrong kind (e.g., a const instead of a type), the lookup functions assumed the item would always match the expected ImplItemId variant and called extract_matches!, which panics on a mismatch. This caused a compiler crash rather than a user-facing diagnostic.


What was the behavior or documentation before?

The compiler panicked when an impl item's name matched a trait item but the kinds differed (e.g., const Foo provided where type Foo was expected).


What is the behavior or documentation after?

The compiler now emits an E2014 diagnostic ("Impl item <kind> <name> is not a member of trait <trait>") for each cross-kind collision and continues compilation without crashing.


Related issue or discussion (if any)

None.


Additional context

The refactor also simplifies the lookup logic by chaining ?, and_then, and ok_or_else instead of nested match blocks.

…the wrong kind

`impl_type_by_trait_type`, `impl_constant_by_trait_constant`, and
`impl_impl_by_trait_impl` looked up the impl item by name and then
`extract_matches!`'d it to the expected `ImplItemId` variant. When an impl
provides an item whose name matches a trait associated item but whose kind
differs (e.g. trait declares `type Foo` and the impl provides `const Foo`),
the extract panicked. These queries are on the mandatory resolution path
(reached via `MyImpl::Foo` in type/value/impl position), so the panic fired
before the separate trait-item-mismatch validation could surface its E2014.

Use `try_extract_matches!(...).ok_or_else(skip_diagnostic)` in all three, so
a wrong-kind item resolves to a skipped diagnostic and the existing E2014
("impl item ... is not a member of trait") is reported instead.

Adds an `expr/test_data/impl` golden covering all three query kinds: a trait
declaring a `type`/`const`/`impl` associated item, an impl providing each
with the wrong kind, referenced so every query runs.

orizi commented Jul 17, 2026

Copy link
Copy Markdown
Collaborator Author

This stack of pull requests is managed by Graphite. Learn more about stacking.

@reviewable-StarkWare

Copy link
Copy Markdown

This change is Reviewable

@orizi
orizi marked this pull request as ready for review July 17, 2026 09:08
@cursor

cursor Bot commented Jul 17, 2026

Copy link
Copy Markdown

PR Summary

Low Risk
Small, localized change in impl–trait item resolution with clearer error handling and a new regression test; no auth or runtime behavior changes.

Overview
Fixes a compiler crash when an impl defines associated items under trait names but with the wrong item kind (e.g. const AsType where the trait expects type AsType).

In impl_type_by_trait_type, impl_constant_by_trait_constant, and impl_impl_by_trait_impl, lookups no longer use panicking extract_matches! on impl_item_by_name results. They use try_extract_matches! so a same-name, wrong-kind entry is treated as missing and returns skip_diagnostic instead of ICE-ing. Validation paths can still emit E2014 (ImplItemNotInTrait) for those mismatched items.

Adds a diagnostics test for cross-kind collisions (const/type/impl swapped) and expected follow-on errors when using those items in code.

Reviewed by Cursor Bugbot for commit 86292dc. Bugbot is set up for automated code reviews on this repo. Configure here.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants