Skip to content

Decoder surface defects: same-named decode() with different encodings, missing re-export, stale stub, drifted registry #431

Description

@ciaranra

Problem

Two public decoder classes expose a method with the same name, decode, that
takes different input encodings, and both accept list[int] from Python, so
mixing them up is silent rather than an error.

  • PyMatchingDecoder.decode(syndrome) takes a dense per-detector vector
    (python/pecos-rslib/src/decoder_bindings.rs:524).
  • TesseractDecoder.decode(detections) takes sparse detector indices
    (python/pecos-rslib/src/decoder_bindings.rs:1586, documented at :1573);
    TesseractDecoder.decode_syndrome is the dense one and densifies before
    delegating (:1608-1616).

Verified on one DEM with the same Python literal [1, 0]:

Tesseract decode([1, 0])           -> observables_mask = 0
Tesseract decode_syndrome([1, 0])  -> observables_mask = 1

A user who reaches for decode on both classes gets a wrong answer from one of
them with no exception raised.

decode_batch is likewise not uniform: PyMatchingDecoder.decode_batch(events, num_shots) returns raw list[list[int]] and requires an explicit shot count,
while TesseractDecoder.decode_batch(syndromes, num_workers=None) returns
result objects (:558-562, :1633-1637).

Separately, MWPM2D and DummyDecoder in the same pecos.decoders namespace
also define decode, with a third protocol entirely (measurement output to
recovery circuit).

Related defects found alongside

  • DemAwareResult is registered in pecos_rslib.decoders but not re-exported
    from pecos.decoders (python/quantum-pecos/src/pecos/decoders/__init__.py),
    so users receive an object they cannot import by name.
  • FusionBlossomDecoder has a Rust from_dem that is not exposed on the
    pyclass (python/pecos-rslib/src/decoder_bindings.rs:666-763), so it is
    reachable only through the string registry.
  • The type stub python/pecos-rslib/pecos_rslib.pyi is stale for this family:
    it declares PyMatchingDecoder.__init__(check_matrix, weights) (real:
    new(num_nodes, num_observables=64)), TesseractResult.correction/.weight
    (real getters: observables_mask, cost, low_confidence),
    TesseractDecoder.__init__(dem_string) (real: from_dem staticmethod), and
    omits DemAwareDecoder/DemAwareResult entirely.
  • A second decoder string registry, decoder_dem_requirement
    (python/pecos-rslib/src/fault_tolerance_bindings.rs:6902-6925), has drifted
    out of sync with create_observable_decoder: belief_matching,
    belief_matching_correlated, belief_find, beamsearch, and perturbed
    raise "Unknown decoder type", while chromobius is listed but is not
    constructible.

Notes

These are the concrete, fixable defects behind #429. Several can be fixed
without any API-shape change, which is worth doing first: re-export
DemAwareResult, expose FusionBlossomDecoder.from_dem, refresh the stub, and
reconcile the two registries.

Found by an adversarial design-review panel on
pecos-docs/design/construction-and-decoding-api-shape.md and verified by
execution against the installed extension.

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugSomething isn't workingpythonPull requests that update python coderustPull requests that update rust codeseverity:highBroken functionality or loud failure in a supported path

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions