https://gcc.gnu.org/g:c7c0d7d99e46cdf2b468ef5768c62de2d082e049
commit r16-7767-gc7c0d7d99e46cdf2b468ef5768c62de2d082e049 Author: Harishankar <[email protected]> Date: Tue Jan 6 19:20:29 2026 +0530 gccrs: Fix ICE in insert_associated_trait_impl due to recursion Recursive const blocks containing trait implementations previously caused an assertion failure (ICE) because the compiler re-visited existing IDs. This patch adds a check to return early if the ID exists, enabling graceful handling of recursion. Fixes Rust-GCC/gccrs#4166 gcc/rust/ChangeLog: * typecheck/rust-typecheck-context.cc (insert_associated_trait_impl): Prevent ICE by checking for existing ID. * typecheck/rust-hir-type-check.h: Update declarations. gcc/testsuite/ChangeLog: * rust/compile/issue-4166.rs: New test. Signed-off-by: Harishankar <[email protected]> Diff: --- gcc/rust/typecheck/rust-hir-type-check.h | 2 +- gcc/rust/typecheck/rust-typecheck-context.cc | 10 +++++++--- gcc/testsuite/rust/compile/issue-4166.rs | 19 +++++++++++++++++++ 3 files changed, 27 insertions(+), 4 deletions(-) diff --git a/gcc/rust/typecheck/rust-hir-type-check.h b/gcc/rust/typecheck/rust-hir-type-check.h index 36a8834ca268..e356f05c0ea6 100644 --- a/gcc/rust/typecheck/rust-hir-type-check.h +++ b/gcc/rust/typecheck/rust-hir-type-check.h @@ -235,7 +235,7 @@ public: void insert_trait_reference (DefId id, TraitReference &&ref); bool lookup_trait_reference (DefId id, TraitReference **ref); - void insert_associated_trait_impl (HirId id, + bool insert_associated_trait_impl (HirId id, AssociatedImplTrait &&associated); bool lookup_associated_trait_impl (HirId id, AssociatedImplTrait **associated); diff --git a/gcc/rust/typecheck/rust-typecheck-context.cc b/gcc/rust/typecheck/rust-typecheck-context.cc index 37f88e97ca9e..f2c186fb063d 100644 --- a/gcc/rust/typecheck/rust-typecheck-context.cc +++ b/gcc/rust/typecheck/rust-typecheck-context.cc @@ -248,13 +248,17 @@ TypeCheckContext::lookup_trait_reference (DefId id, TraitReference **ref) return true; } -void +bool TypeCheckContext::insert_associated_trait_impl ( HirId id, AssociatedImplTrait &&associated) { - rust_assert (associated_impl_traits.find (id) - == associated_impl_traits.end ()); + auto it = associated_impl_traits.find (id); + if (it != associated_impl_traits.end ()) + { + return false; + } associated_impl_traits.emplace (id, std::move (associated)); + return true; } bool diff --git a/gcc/testsuite/rust/compile/issue-4166.rs b/gcc/testsuite/rust/compile/issue-4166.rs new file mode 100644 index 000000000000..b9042d88cdce --- /dev/null +++ b/gcc/testsuite/rust/compile/issue-4166.rs @@ -0,0 +1,19 @@ + +pub trait Foo { + type Bar; + fn foo(bar: Self::bar); // { dg-error "failed to resolve path segment using an impl Probe" } +} + +pub struct FooImpl; + +const foo_impl: () = { + impl Foo for FooImpl { + type Bar = (); + fn foo(_bar: Self::Bar) { // { dg-error "method .foo. has an incompatible type|mismatched types" } + // This is the recursive reference that used to cause the ICE + let () = foo_impl; + } + } +}; + +fn main() {} \ No newline at end of file
