Skip to content

shared+rebase warns "UNSOUND" unconditionally — inaccurate for reloc-carrying inputs (the path pack-rebase/share-stack are built on) #386

Description

@avrabe

The problem

--memory shared --address-rebase emits an unconditional "UNSOUND" warning
(meld-core/src/lib.rs:539-549) — including for inputs that carry full
--emit-relocs metadata, where the transform is not unsound and is the path
meld's whole MCU feature line is built on.

memory strategy: explicit shared-memory + address rebasing is UNSOUND
for components that access memory via computed pointers (#326) — the
dynamic address operand of ordinary loads/stores is not rebased, so
per-component memory can silently collide. Prefer `--memory multi` ...

The warning predates the reloc consumer. Since #326#340 shipped, a
reloc-carrying input is rebased at the source point — every reloc-flagged
i32.const address is relocated at its origin, so a pointer computed from it is
correct by construction. The blanket claim describes the pre-consumer world.

Why it matters (a safety tool crying wolf)

This warning fires on the supported, supplier-validated path:

So every gale production build prints "UNSOUND" about a transform we ship,
document, and have supplier-validated. In a functional-safety tool that is worse
than noise: it trains users to ignore warnings, including the precise one that
does matter.

The precise warning already exists

address_strategy.rs:104-115 already warns per-module, only on the no-reloc path,
naming the actual residual (#339: an absolute address used as a value, no reloc
coverage) and the remedy (--emit-relocs). And the genuinely dangerous case —
no-reloc with direct load/store — is already a hard error (path-F
MissingRelocMetadata, address_strategy.rs:87-92).

So the blanket warning is both redundant (a better-targeted one exists) and
inaccurate (it fires where the risk does not apply).

Proposal

  1. Make the lib.rs warning conditional — fire only when at least one input
    lacks reloc metadata (reloc::has_reloc_metadata), or drop it entirely in
    favour of the existing per-module address_strategy warning. A fully
    reloc-covered fuse should be quiet.
  2. Doc-rot: lib.rs:605 references warn_if_unsound_rebasing — no such
    function exists. Fix or remove the reference.
  3. Open question (propose, don't decide): should Auto reconsider?
    resolve_auto_memory_strategy (lib.rs:553-612) never selects shared+rebase,
    citing the same stale fuse --memory auto/shared silently corrupts memory across components: load/store dynamic addresses are not rebased (no memory.grow; distinct from #172/#299) #326 rationale — even when every input carries relocs and
    nothing grows. It could plausibly select shared+rebase when all inputs are
    reloc-covered. Caveat: if any input lacks relocs and does direct memory access,
    path-F would turn a currently-working multi-memory fuse into a hard error, so
    the condition must be "all inputs reloc-covered", and ADR-4 ("explicit, not
    auto" for attested builds) argues for leaving Auto conservative regardless.
    Flagging for a decision rather than proposing the change.

Items 1–2 are small and clearly right. Item 3 is a defaults question for the
maintainer.

Not a corruption bug

To be clear about severity: this is messaging accuracy + a stale default, not
a soundness defect. Nothing is mis-compiled. The cost is warning fatigue on the
supported path and a misleading picture of what meld can do by default.

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