Skip to content

Value-copy helper identity relies on scattered structural-mangle canonicalization #1588

Description

@gfx

Problem

Value-copy ($value_copy$) helpers and array-clone element helpers are identified by a structural name mangle (TypeTable::mangle_type_arg_for_generic) instead of by a canonical type identity. This compensates for the TypeTable interning the same logical type under multiple TypeIds:

  • A GenericInstance and its monomorphized Struct coexist as distinct ids — monomorphization mints a new Struct id and leaves the GenericInstance id live (linkage is kept in Monomorphizer.type_substitutions, not in the table).
  • List<T> / tuples intentionally stay GenericInstance, so they get a fresh id whenever their argument ids diverge.

Because there is no canonical TypeId, several passes independently re-derive the mangle to key/root the same helper:

  • lower/plan/value_copy/synthesize.rs — names the helper
  • wir_build/functions.rs, wir_build/calls.rs — stamp value_copy_mangle / element_copy_mangle
  • optimize/dce.rs — NIR DCE rooting
  • wir_optimize/dce.rs, wir_optimize/util.rs — WIR DCE rooting / SROA pinning
  • codegen/emit.rsArrayClone resolution

Why it matters

  • Correctness fragility. A helper's definition and its references derive identity from independent mangle computations that must agree byte-for-byte. If the mangle is not injective, distinct types collapse onto one helper and the pipeline emits an invalid Wasm module. For example, a bare Array<Foo> whose element Foo is a same-named struct from two different modules collapses onto a single helper whose one concrete signature then mismatches the other array's ref type. Other collision vectors are plausible.
  • Altitude. Structural identity is re-derived at ~6 sites rather than assigned once.
  • Cost. Allocating, recursive string mangling on rooting and codegen paths.

Direction

Give value-copy helpers a single, assigned-once canonical identity that consumers reference by id, with the structural key computed in exactly one authority.

One load-bearing constraint to respect: the mangle is robust because it is a pure function of structure — an unseen duplicate TypeId still resolves correctly. Any replacement must preserve that property, or eliminate the duplicate interning it compensates for. Note that some of the duplication is intentional (List/tuple staying GenericInstance; monomorphization needing to see raw GenericInstances), so removing duplicate interning is not automatically the answer.

The above is only one example. This should be approached from a zero base and designed for the best long-term maintainability, not anchored to this sketch.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions