Fix cross-module ref-type iterator bug and add return/for-of type checks#727
Merged
Fix cross-module ref-type iterator bug and add return/for-of type checks#727
Conversation
The monomorphizer incorrectly selected Array<T>^IntoIterator::into_iter instead of &^IntoIterator::into_iter when iterating &Array<T> inside generic functions. This caused Wasm GC type mismatches when ArrayIter and ArrayRefIter had different type indices across module boundaries. Root cause: resolve_method_call_substitution in func_inst.rs overwrote the LocalMethodName's base_struct_name from "&" to "Array" by unwrapping the receiver's reference type. This lost the ref-type impl identity, causing the wrong generic template to be instantiated. Three fixes: 1. Propagate is_ref_impl from MethodInfo to LocalMethodName in resolver 2. Preserve base_struct_name for ref-type impls in monomorphizer 3. Fix Array::iter() to construct ArrayIter directly instead of calling self.into_iter() which returns ArrayRefIter (type mismatch) https://claude.ai/code/session_01Psntc941Uh8sx4iWuvy8Fa
The cross_module_type_identity test is no longer TODO-marked — the loader fix for duplicate ModuleSource identities is already in place. https://claude.ai/code/session_01Psntc941Uh8sx4iWuvy8Fa
on-task-done regenerated WIR golden files reflecting the correct iterator template selection for ref-type impls. https://claude.ai/code/session_01Psntc941Uh8sx4iWuvy8Fa
Same pattern as the Array::iter() fix — calling self.into_iter() on &self dispatches to the wrong IntoIterator impl after the ref-type monomorphization fix. https://claude.ai/code/session_01Psntc941Uh8sx4iWuvy8Fa
- Emit "does not implement IntoIterator" when for-of iterable lacks the trait - Emit "does not implement Iterator" when the iterator type lacks next() - Add e2e test fixtures for both error cases - Fix TreeSet::iter() to construct TreeSetIter directly (same pattern as the Array::iter() fix) https://claude.ai/code/session_01Psntc941Uh8sx4iWuvy8Fa
Working tree is dirtyIntegrity checks produced the following changes: Please run |
Previously `fn foo() -> i32 { return "hello"; }` compiled without error,
producing invalid Wasm. Now the resolver checks that the return value's
type matches the declared return type and emits a compile error on
mismatch.
https://claude.ai/code/session_01Psntc941Uh8sx4iWuvy8Fa
Remove base_type_name fallback — cross-module types must have the same TypeId. Add test for same-name structs from different modules correctly producing a type mismatch error. Also fix a real bug found by this check: u8::try_from(u16) was returning Result::<u16, ConvertError> instead of Result::<u8, ...>. Skip unresolved generics (TypeParam, TypePack, AssocTypeProjection, GenericInstance with params) and function types from the check, as these are resolved after monomorphization. https://claude.ai/code/session_01Psntc941Uh8sx4iWuvy8Fa
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.
Summary
Array^IntoIterator::into_iter(returnsArrayIter) instead of&^IntoIterator::into_iter(returnsArrayRefIter) when iterating&Array<T>inside generic functions. Root cause:resolve_method_call_substitutionoverwrotebase_struct_namefrom"&"to"Array"by unwrapping the receiver's reference, and the resolver didn't propagateis_ref_impltoLocalMethodName.Array::iter()andTreeSet::iter(): Both calledself.into_iter()which dispatched to the&Timpl returning the wrong iterator type. Now construct iterators directly.fn foo() -> i32 { return "hello"; }previously compiled silently — now emits a compile error. Uses strict TypeId comparison (no base_type_name fallback). Found and fixed a real stdlib bug:u8::try_from(u16)was returningResult::<u16, ConvertError>.Test plan
on-task-donepasses (format, clippy, golden fixtures, test-wado)#![TODO]fixtures now pass:cross_module_variant_iter,test_world_variant_generic,test_world_variant_generic_run,single_module_variant_itererror_return_type_mismatch,error_return_cross_module_same_name,error_for_of_no_into_iterator,error_for_of_no_iteratorhttps://claude.ai/code/session_01Psntc941Uh8sx4iWuvy8Fa