Skip to content

markused: mark mut-receiver interface implementors (fix -skip-unused dropping anon fn)#27380

Open
medvednikov wants to merge 1 commit into
masterfrom
fix-27354-skip-unused-iface-anon-fn
Open

markused: mark mut-receiver interface implementors (fix -skip-unused dropping anon fn)#27380
medvednikov wants to merge 1 commit into
masterfrom
fix-27354-skip-unused-iface-anon-fn

Conversation

@medvednikov

Copy link
Copy Markdown
Member

Description

Fixes #27354.

An anonymous function passed as a C callback argument inside a method that is reached only via interface dispatch on a mut receiver was dropped by -skip-unused (the default), so the C compiler failed:

error: use of undeclared identifier 'anon_fn_..._145'
  atexit(anon_fn_..._145);

Building with -no-skip-unused worked, pinning the fault to the used-functions analysis.

Root cause

markused's interface walk (mark_by_sym, the ast.Interface arm) iterated only isym.info.types to find implementing types and walk their interface-method bodies. But the checker stores implementors that require a mutable receiver (e.g. fn (mut i Impl) setup()) in isym.info.mut_types, not types. Those method bodies were therefore never walked, and the symbols they reference (here, the anon fn argument) were pruned, even though cgen still emits the method via the interface vtable adapter.

Fix

Walk isym.info.implementor_types(true) instead, the existing helper that merges types with mut_types (deduplicated by idx). This only ever adds implementors to the walk, so it cannot introduce new undeclared-symbol errors — worst case is marginally less aggressive pruning for some mut-receiver interface methods that were incorrectly skipped.

Verification

  • The reproducer now compiles and runs under default -skip-unused, printing done.
  • Added regression test vlib/v/tests/skip_unused/interface_mut_receiver_anon_fn.{vv,run.out} (run by compiler_errors_test.v).
  • Compiler self-compiles cleanly; all 96 vlib/v/tests/interfaces/ tests pass, plus generic_fn_instantiation_pruning_test.v and unused_fn_fixed_array_ret_test.v.

…ropping anon fn)

An anon fn passed to a C callback inside a method reached only via interface
dispatch on a `mut` receiver was dropped by -skip-unused (the default), so the
generated C failed with `use of undeclared identifier 'anon_fn_...'`.

markused's interface walk iterated only `isym.info.types`, but the checker
stores implementors that require a mutable receiver (e.g. `fn (mut i Impl)
setup()`) in `isym.info.mut_types`. Those method bodies were therefore never
walked, and symbols they reference (here, the anon fn argument) were pruned.

Walk `isym.info.implementor_types(true)` instead, which merges `types` and
`mut_types` (deduplicated by idx). This only ever adds implementors to the
walk, so it cannot cause new undeclared-symbol errors.

Fixes #27354
@chatgpt-codex-connector

Copy link
Copy Markdown

You have reached your Codex usage limits for code reviews. You can see your limits in the Codex usage dashboard.

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.

cgen, skip-unused: anon fn passed to a C callback (via interface-dispatched method) is not marked used

1 participant