Skip to content

Tracking PR fo v0.24.0 release#895

Draft
bobbinth wants to merge 47 commits intomainfrom
next
Draft

Tracking PR fo v0.24.0 release#895
bobbinth wants to merge 47 commits intomainfrom
next

Conversation

@bobbinth
Copy link
Copy Markdown
Contributor

This is a tracking PR for v0.24.0 release.

bobbinth and others added 30 commits March 11, 2026 16:35
* mmr: reject oversized forests to prevent num_nodes panics

Forest deserialization previously accepted unbounded usize values. For values > usize::MAX/2 + 1, Forest::num_nodes asserted and would panic when downstream APIs (peaks/open/delta) were called.

An attacker could craft a serialized MMR with forest = usize::MAX/2 + 2 to crash consumers after deserialization.

This change enforces a maximum forest size at construction and deserialization, removes infallible constructors in favor of fallible ones, makes leaf appends return errors, and adds tests to cover oversize and iterator growth paths so oversized inputs are rejected before any panic can occur.

* mmr: cap forest size safely

* mmr: simplify append flow and document forest invariant

* mmr: trust apply invariants for new_peaks

* mmr: hard-cap max leaves to 2^k-1 and simplify xor/or

* mmr: remove redundant bounds checks and harden invariants

* mmr: centralize mask->node count helper usage
This changes `LargeSmtForest::entries` to return an iterator over items
that are `Result<TreeEntry>` instead of bare `TreeEntry`, ensuring that
the potential failure of iteration in the backend is communicated
clearly to the caller performing the iteration.

We also add benchmarks to the iteration in order to confirm that the
changes incur no performance impact.
This change makes it so all SMT operations that operate on batches of
key-value pairs will reject any input where the same key occurs more
than once. This ensures that all of the various SMT implementations are
coherent on the results they provide as there are no longer
order-dependent computations.

This commit introduces no measurable performance change for any impacted
code path. No performance regressions are included.
This function was superseded by the change in #847 to have `Word`
compare lexicographically. This commit removes the last few uses and
replaces them with calls to the `Ord` implementation for `Word` instead,
simplifying the codebase.
This commit makes it possible for all writes in the persistent backend
of the LargeSmtForest to be flushed to disk in a manner that the user
decides. The default remains `false`, providing higher write performance
but less durability, and the user can set it to `true` for higher
durability but lower write performance.
This commit adds the `add_lineages` batch endpoint to the forest,
providing a far more efficient way to add many new lineages at once than
simply calling `add_lineage` in a loop.

It originally experimented with additional `open_many` and `get_many`
endpoints, but these proved no more efficient than simply calling `open`
and `get` in a loop and have hence been removed. They are mentioned here
for posterity.

The new `add_lineages` endpoint is accompanied by comprehensive tests,
as well as benchmarks to establish baseline performance. It is faster
than calling `add_lineage` in a loop as soon as more than five lineages
are being added when used in conjunction with the persistent backend,
and when it is slower it is not by a significant amount. It is highly
recommended to use this endpoint when adding multiple lineages at once.

The exact performance profile is backend-dependent.

This commit also includes some additional benchmarks for the large
forest that were necessary to validate that performance had not changed
for existing endpoints while making changes.
* Add curated Clippy guardrails

Port the curated xclippy/xclippy-fix workflow from miden-vm to this workspace.\n\nEnable only the optional Clippy lints that currently pass without code fixes, wire the Make targets and existing lint CI to use that curated set.

* Preserve xclippy alias order

Exclude .cargo/config.toml from Taplo formatting and restore the Cargo alias argv order so the clippy CI job invokes the xclippy aliases correctly.
The type was previously used to perform lexicographic comparisons
between words, but that behavior is now encapsulated in the default
`Ord` instance for word, so the type is unnecessary.
This helps avoid the need for ser/de helpers due to the orphan rule, and
is a simple change that relies on the existing `&str` ser/de machinery.
It also now implements `Serializable` for `String` in terms of `str` for
consistency.
This commit removes the `WORD_SIZE_FELTS` and `WORD_SIZE_BYTES`
module-level constants in favor of the associated constants
`Word::NUM_ELEMENTS` and `Word::SERIALIZED_SIZE` respectively.
This makes the API more consistent while incurring no functional or
performance regressions.

It also removes `WORD_SIZE` from `miden-crypto` to help harmonize usage
as the constant's name was potentially misleading. If we are making a
breaking API change anyway, we might as well harmonize usages wholesale.
The trait implementation was both unused and caused type inference
issues, so removing it is the simplest choice.
chore(deps): drop `patch` versioning for remaining plonky3 deps
This commit eagerly computes historical entry counts when creating the
history deltas, making it possible to provide the true historical entry
counts without traversing the historical entries of the tree. This
drastically improves the performance of `entry_count`, while avoiding
any regressions in other code paths.
feat: update Poseidon2 to match upstream P3
AlexWaker and others added 17 commits April 4, 2026 03:41
…verage (#886)

* first commit

* delete unnecessary contents

* a huge adjustment

* delete property_tests

* fix format

* fix benchmark bug

* delete temp contents

* fix suggestions

* make clipy

* format check
Prior to this commit, `Felt::new` did not perform reduction, silently
accepting any `u64` value and potentially leading to confusing results.
Now it returns an error if the input value is invalid.

The old behavior, which is useful in places not limited to tests, is now
available as `Felt::new_unchecked`.

Both the native and WASM backends have undergone these changes, ensuring
that construction is uniform regardless of the implementation being
compiled.
* Initial commit: Miden-specific Plonky3 crates

* fix: gate debug constraint checking behind cfg(debug_assertions)

* ci: Add CI workflows and Makefile for build automation

Adds basic CI/CD infrastructure and Makefile (like miden-crypto):

**CI Workflows:**
- lint.yml
- test.yml
- build.yml

**Makefile:**
- Linting tasks: format, clippy, toml, typos, cargo-sort, machete
- Testing tasks: test, test-parallel, test-release
- Build tasks: build, build-no-std, build-avx2, build-avx512

**Dependency Updates:**
- Bump criterion from 0.5.1 to 0.8 to match Plonky3 upstream

* chore: apply formatting and linting fixes

- Run rustfmt to fix import ordering
- Fix typos: entires -> entries, inpsired -> inspired, takeing -> taking
- Sort Cargo.toml dependencies with cargo-sort
- Format TOML files with taplo

* chore: remove unused p3-air dependency and ignore paste in machete

- Remove unused p3-air dependency from p3-miden-prover
- Add cargo-machete ignore for paste in p3-miden-goldilocks
  (paste is used via macros which machete cannot detect)

All tests pass and cargo-machete is now clean.

* fix: resolve cargo doc and cargo-sort CI failures

- Fix rustdoc URL warnings by wrapping URLs in angle brackets
- Fix rustdoc private link warnings by using backticks instead of link syntax
- Sort workspace Cargo.toml dependencies with cargo-sort

All CI linting checks now pass (doc, cargo-sort).

* chore: add dual MIT/Apache-2.0 license

Add LICENSE-MIT and LICENSE-APACHE files matching the dual licensing
setup used in miden-crypto. The Cargo.toml workspace already specifies
"MIT OR Apache-2.0" as the license.

Copyright (c) 2025 Miden

* docs: add README for Miden Plonky3 crates

Add concise README documenting the five Miden-specific Plonky3 crates
and their modifications from upstream. Follows the style of p3-playground
for brevity while covering key changes and compatibility information.

* chore: migrate Plonky3 dependencies from git to crates.io v0.4.1

Replace all Plonky3 git dependencies pointing to main branch with published
crates.io version 0.4.1. This provides more stable and reproducible builds
by using versioned releases instead of tracking the main branch.

* feat: add workspace release automation

Add GitHub Actions workflows to verify and publish workspace crates.

The dry-run workflow runs `cargo publish --workspace --dry-run` on every
push to main, ensuring the workspace stays releasable. The publish workflow
triggers on GitHub releases and publishes all crates to crates.io.

Both workflows verify MSRV (Rust 1.85) and clean the package directory
before running to avoid stale state. The publish workflow includes a safety
check that the release tag matches main HEAD.

Setup requires adding CARGO_REGISTRY_TOKEN to the crates.io environment
in repository settings.

* chore: Remove Cargo sort from CI (conflicts with taplo)

* chore: beef up crates metadata

* refactor: remove `p3-miden-goldilocks`

* fixup! refactor: remove `p3-miden-goldilocks`

* chore: update version

* refactor: update Pcs trait implementation for plonky3 compatibility

- Update hiding_pcs.rs to match upstream plonky3 implementation
  - Add get_quotient_ldes and commit_ldes methods
  - Add commit_preprocessing and get_evaluations_on_domain_no_random
  - Update get_opt_randomization_poly_commitment to accept iterator
  - Update open to delegate to open_with_preprocessing

- Add missing Pcs trait methods to two_adic_pcs.rs
  - Add get_quotient_ldes method
  - Add commit_ldes method

- Fix prover calls to get_opt_randomization_poly_commitment
  - Wrap single domain in array to satisfy new iterator signature

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* chore: update to latest plonky3

* ci: add changelog and PR changelog check

Add CHANGELOG.md documenting v0.4.0 and upcoming v0.4.2 releases.
Add CI workflow that requires CHANGELOG updates on PRs (skippable
with "no changelog" label).

* feat(symmetric): add StatefulHasher trait and implementations

Add p3-miden-symmetric crate forked from p3-symmetric v0.4.2 with:

- StatefulHasher trait for stateful sponge-like hashers
- StatefulSponge wrapper around CryptographicPermutation
- SerializingStatefulSponge adapter for field-to-binary serialization
- ChainingHasher adapter using H(state || input) chaining mode
- Test helpers (MockHasher, MockPermutation) for testing

These abstractions are required by the lifted Merkle tree commitment
scheme (LMCS) for incremental row absorption.

Co-authored-by: Adrian Hamelink <adrian.hamelink@gmail.com>

* feat(field): add FieldArray utilities and PackedFieldExtension methods

Add p3-miden-field crate forked from p3-field v0.4.2 with:

FieldArray utilities:
- map() and map_array() for element-wise transformations
- Index and IndexMut implementations for direct element access
- slice_as_arrays(), mut_slice_as_mut_arrays() for zero-cost transmutes
- arrays_as_slice(), mut_arrays_as_mut_slice() for reverse conversions

PackedFieldExtension methods:
- extract_lane() to extract extension field element at SIMD lane
- to_ext_slice() to unpack packed extension into slice
- pack_ext_columns() to pack columns from multiple rows
- pack_columns() and unpack_columns() on PackedValue trait

These utilities support efficient SIMD operations in the lifted PCS.

Co-authored-by: Adrian Hamelink <adrian.hamelink@gmail.com>

* feat(matrix): add Matrix impl for references and batched dot product

Add p3-miden-matrix crate forked from p3-matrix v0.4.2 with:

- Matrix<T> impl for &M enabling lightweight views over references
- columnwise_dot_product_batched() for computing multiple dot products
  in a single pass over the matrix, reducing memory bandwidth

The reference impl allows using &Matrix anywhere Matrix is expected,
useful for lifted/strided views without cloning.

The batched dot product enables efficient multi-point evaluation in
the DEEP quotient computation by loading each matrix row once.

Note: Unit tests are disabled as they require field types implementing
p3_miden_field traits. Functionality is tested by p3-miden-lifted.

Co-authored-by: Adrian Hamelink <adrian.hamelink@gmail.com>

* feat(lifted): add merkle_tree module with LMCS commitment scheme

Add the lifted Merkle tree commitment scheme that supports:
- Matrices with varying power-of-two heights via upsampling
- Non-hiding (MerkleTreeLmcs) and hiding (MerkleTreeHidingLmcs) variants
- Integration with p3_commit::Mmcs trait for PCS compatibility

The merkle_tree module provides:
- `LiftedMerkleTree`: Core tree structure with incremental sponge hashing
- `MerkleTreeLmcs`: MMCS implementation for public commitments
- `MerkleTreeHidingLmcs`: Zero-knowledge variant with random salt rows

Also updates p3-miden-symmetric to use upstream p3_symmetric permutation
traits for compatibility with p3_baby_bear Poseidon2 implementations.

Co-authored-by: Adrian Hamelink <adrian.hamelink@gmail.com>

* feat(lifted): add DEEP quotient module for batched polynomial evaluation

Add deep quotient construction enabling efficient batched polynomial
evaluation proofs via barycentric interpolation. Uses extension traits
to bridge compatibility between forked and upstream plonky3 crates.

Co-authored-by: Adrian Hamelink <adrian.hamelink@gmail.com>

* feat(lifted): add FRI protocol module for low-degree testing

Add FRI (Fast Reed-Solomon IOP) commit/verify implementation with
configurable folding arities (2 or 4) and final polynomial degree.
Includes SIMD-optimized matrix folding for performance.

Co-authored-by: Adrian Hamelink <adrian.hamelink@gmail.com>

* feat(lifted): add PCS module combining DEEP quotient and FRI

Add complete polynomial commitment scheme implementation with high-level
open() and verify() functions that orchestrate DEEP quotient construction
and FRI low-degree testing into a unified PCS interface.

Co-authored-by: Adrian Hamelink <adrian.hamelink@gmail.com>

* refactor: remove unused p3-miden-field and p3-miden-matrix crates

These crates were declared as dependencies but never imported. The
functionality they provided (columnwise_dot_product_batched, Matrix
impl for &M) is now implemented via extension traits in p3-miden-lifted,
which is cleaner and avoids maintaining full fork crates.

Also updates README to document p3-miden-symmetric and p3-miden-lifted.

* fix: CI failures for typos, unused deps, docs, and cross-platform tests

- typos: Use `i·y` instead of `iy` in FFT comments (middle dot avoids
  false positive from typos checker)
- unused deps: Remove unused serde dependency from p3-miden-symmetric
- docs: Fix broken intra-doc link to non-existent `Lifting::Upsample`
- tests: Ensure matrix_scenarios() heights are at least 1 even when
  P::WIDTH=1 (no SIMD) on platforms without AVX support

* refactor(lifted): consolidate duplicate PackedFieldExtensionExt trait

Move the duplicate PackedFieldExtensionExt trait from fri/fold.rs and
deep/prover.rs into utils.rs as a single shared definition.

Also remove the unnecessary PackedExtFieldExt trait from interpolate.rs,
which was just wrapping extract() as extract_lane() with no added value.

* chore: Changelog

* refactor(lifted): simplify FRI types and tighten visibility

- Rename CommitPhaseData → FriPolys, CommitPhaseProof → FriOracle
- Remove FriChallenges struct; betas now sampled inside FriOracle::new
- FriPolys::new returns Self instead of tuple, takes &[EF] instead of Vec
- FriOracle::verify_query derives log_domain_size internally
- Change pub → pub(crate) for internal fields (DeepChallenges, OpeningClaim, FriPolys)
- Remove DeepPoly::evals() accessor; rename field to deep_evals
- Flatten Proof struct: fri_commitments + fri_final_poly instead of wrapper

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* feat(lifted): add proof-of-work grinding and encapsulate transcript flow

Integrate proof-of-work grinding at three strategic points in the protocol
to prevent grinding attacks, and restructure the API to encapsulate all
Fiat-Shamir transcript operations within constructors.

## Proof-of-Work Integration

Add grinding witnesses at three points for soundness hardening:
- **DEEP challenges (α, β)**: Configured via `DeepParams::proof_of_work_bits`
- **FRI per-round beta**: Configured via `FriParams::proof_of_work_bits`
- **Query indices**: Configured via `PcsConfig::query_proof_of_work_bits`

Each grinding point stores its witness in the proof structure, which the
verifier checks before sampling the corresponding challenges.

## API Restructuring

Encapsulate transcript operations within constructors to enforce correct
Fiat-Shamir ordering and simplify the API:

- `DeepPoly::new`: Now handles observe → grind → sample internally,
  returns `(DeepPoly, DeepProof)` tuple
- `DeepOracle::new`: Now handles observe → check_witness → sample,
  takes `DeepProof` parameter
- `FriPolys::new`: Now grinds per-round internally,
  returns `(FriPolys, FriProof)` tuple
- `FriOracle::new`: Now checks per-round PoW witnesses,
  takes `FriProof` parameter, returns `Result`

## Type Changes

**Removed:**
- `DeepChallenges<EF>`: Replaced by internal challenge sampling
- `OpeningClaim<EF>`: Parameters passed directly to constructors
- `PointQuotients::points()`: Unused accessor

**Added:**
- `DeepParams`: Configuration struct (alignment, proof_of_work_bits)
- `DeepProof<Witness>`: Contains DEEP grinding witness
- `FriProof<EF, FriMmcs, Witness>`: Contains commitments, final_poly,
  and per-round grinding witnesses

**Modified:**
- `FriParams`: Removed `num_queries`, added `proof_of_work_bits`
- `PcsConfig`: Now contains `deep: DeepParams`, `fri: FriParams`,
  `num_queries`, and `query_proof_of_work_bits`
- `Proof`: Now generic over `Witness` type, contains `DeepProof`,
  `FriProof`, and `query_pow_witness`
- `DeepError`: Now enum with `StructureMismatch` and `InvalidPowWitness`
- `FriError`: Added `InvalidPowWitness` variant
- `PcsError`: Added `InvalidFriPowWitness` and `InvalidQueryPowWitness`

## Visibility Tightening

- `deep::{interpolate, prover, verifier}` → `pub(crate)`
- `fri::{fold, prover, verifier}` → `pub(crate)`
- `utils` module → `pub(crate)`
- `derive_coeffs_from_challenge` → private
- `PackedFieldExtensionExt` trait → `pub(crate)`
- Various helper functions → `pub(crate)`

## Parameter Ordering

Standardized to `(params, mmcs, ...)` in internal modules.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* refactor(lifted): move MatrixExt trait to utils

Consolidate extension traits by moving MatrixExt from deep/interpolate.rs
to utils.rs alongside PackedFieldExtensionExt.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* refactor(lifted): replace p3-miden-symmetric with p3-miden-stateful-hasher

Replace the p3-miden-symmetric crate with the new p3-miden-stateful-hasher
crate from upstream plonky3. The new crate provides a cleaner stateful
hashing API with the Alignable trait for padding semantics.

Import changes:
- StatefulHasher, StatefulSponge -> p3_miden_stateful_hasher
- Hash, PseudoCompressionFunction, TruncatedPermutation -> p3_symmetric

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* refactor(lifted): simplify PcsError by embedding FriError

- Embed FriError directly into PcsError using #[from], removing manual
  error mapping and unreachable!() branches
- Move PcsError from proof.rs to mod.rs for consistency with other modules
- Replace verifier expect() with proper error return (NoCommitments)
- Remove redundant error variants (FriMmcsError, FriFoldingError,
  FinalPolyMismatch, InvalidFriPowWitness) now covered by embedded FriError

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* feat(fri): add support for arity 8 folding

* refactor(fri): split `fold.rs` into multiple modules

* feat: Handle aux boundary values (#7)

* feat: Handle aux boundary values

* chore: fmt and clippy fixes

* fix: remove feature gate on prover_row_to_ext, fix make build

* chore: update CHANGELOG.md

* refactor: Remove Option in aux_finals field

* refactor: return slice instead of Vec for bus_types()

* chore: Add Sync bound to StarkConfig

* refactor: move packed_aux_bus_boundary_values computation outside loop

* chore: Revert "add Sync bound to StarkConfig"

This reverts commit 45e4ac89cf8ce9991608490a80432db94da1f609.

* chore: cargo fmt and clippy fixes

* refactor(fri): replace trait-based folding with enum-based FriFold struct

Replace the `FriFold<const ARITY>` trait and marker types (`FriFold2`,
`FriFold4`, `FriFold8`) with a single `FriFold` struct that encapsulates
the folding arity. This simplifies the API and reduces generic complexity.

## Architecture Changes

- **Trait → Struct**: `FriFold<const ARITY>` trait replaced with `FriFold`
  struct containing `log_arity: usize` field
- **Marker types removed**: `FriFold2`, `FriFold4`, `FriFold8` no longer
  exported; arity-specific logic now in private `fold_evals()` functions
- **Const constructors**: Added `FriFold::ARITY_2`, `ARITY_4`, `ARITY_8`
  for ergonomic, compile-time-safe construction
- **Runtime dispatch**: `fold_evals()` and `fold_matrix()` now dispatch
  via match on `log_arity` instead of trait method resolution

## API Changes

- `FriParams::log_folding_factor: usize` → `FriParams::fold: FriFold`
- `FriOracle<EF, FriMmcs>` → `FriOracle<F, EF, FriMmcs>` (F now on type)
- `verify_query::<F>(...)` → `verify_query(...)` (no turbofish needed)
- `FriParams::num_rounds()` and `final_poly_degree()` no longer `const fn`

## Code Organization

- Butterfly helpers (`dit_butterfly`, `twiddle_free_butterfly`) moved from
  `fold/mod.rs` to `fold/arity8.rs` (only consumer)
- Tests consolidated in `fold/mod.rs` with parameterized test functions:
  - `test_fold_correctness()` - verifies folding against Horner evaluation
  - `test_fold_evals_naive_dft()` - verifies against `NaiveDft` coset evals
  - `test_fold_matrix_scalar_packed_equivalence()` - scalar vs SIMD paths
  - `test_folding_preserves_low_degree()` - degree reduction property
- Removed redundant per-arity compile-time type tests

## Bug Fixes

- Fixed latent bug in `prover.rs` where arity-8 match arm incorrectly used
  `4` instead of `3` for `log_arity`

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* refactor(lifted): reorganize proof types into dedicated modules with accessors

Split monolithic modules into focused submodules for better organization:
- deep: extract proof.rs (DeepProof, DeepQuery) and utils.rs (observe_evals, reduce_with_powers)
- fri: extract proof.rs (FriProof, FriQuery)
- pcs: extract prover.rs and verifier.rs from mod.rs

Improve encapsulation of proof types:
- Make proof modules private with explicit re-exports at module root
- Add public accessor methods for read-only inspection of all proof fields
- Use pub(super) visibility for struct fields to prevent external mutation

Other changes:
- Move MatrixGroupEvals from deep/mod.rs to utils.rs
- Move error types (DeepError, FriError, PcsError) to verifier modules
- Introduce FriQuery wrapper type for FRI round openings
- Remove unused PhantomData<F> and QueryProof::new() constructor

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* Update CHANGELOG.md

* refactor(workspace): extract LMCS crate and add dev-utils with benchmarks

This refactoring improves code organization by extracting the Lifted Matrix
Commitment Scheme into a standalone crate and consolidating shared test/benchmark
infrastructure.

New crates:
- p3-miden-lmcs: Standalone LMCS implementation extracted from p3-miden-lifted
  - MerkleTreeLmcs, MerkleTreeHidingLmcs, LiftedMerkleTree
  - No external dependencies on p3-miden-lifted internals

- p3-miden-dev-utils: Shared development utilities
  - Benchmark infrastructure (criterion configs, matrix generation)
  - Test fixtures for BabyBear/Goldilocks with Poseidon2/Keccak
  - BenchScenario and PcsScenario traits for generic benchmarking
  - Matrix utilities (lift, concatenate, random LDE generation)

New benchmarks:
- p3-miden-lifted: PCS comparison, FRI fold, FRI comparison, DEEP quotient
- p3-miden-lmcs: LMCS vs MMCS, Merkle commit with ExtensionMmcs

Changes to p3-miden-lifted:
- Removed merkle_tree module (moved to p3-miden-lmcs)
- Test utilities now re-exported from p3-miden-dev-utils
- Made bit_reversed_coset_points public for benchmark use

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* refactor(stateful-hasher): make State an associated type

Change StatefulHasher trait from 3 generic parameters (Item, State, Out)
to 2 parameters (Item, Out) with State as an associated type.

- Add `type State` associated type to StatefulHasher trait
- Add `hash_rows` convenience method (requires State: Default)
- Update StatefulSponge, SerializingStatefulSponge, ChainingHasher impls
- Update LMCS bounds to use associated type syntax

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* refactor(lmcs): add utils module with PackedValueExt and upsample_matrix

- Move PackedValueExt trait from lifted_tree to lmcs/utils
- Move lift_matrix from dev-utils to lmcs/utils as upsample_matrix
- Switch from local unpack_columns to PD::unpack_into

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* feat(lmcs): add compact multi-opening proof module

Add proof structures for efficiently opening multiple Merkle leaves
with shared sibling deduplication. Includes NodeIndex heap indexing,
CompactProof with BTreeMap-based storage, and PartialTree for
verification with strict validation of proof completeness.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* refactor(lifted): unify MMCS types and simplify proof structs

- Unify InputMmcs and FriMmcs into single Mmcs<F> parameter
- Use FlatMatrixView for zero-copy EF→F flattening in FRI prover
- Remove EF type param and PhantomData from FriQuery, QueryProof
- Remove PhantomData markers from FriPolys and FriOracle
- Use where clauses for structs with >2 type parameters
- Remove FriMmcs type alias and test_fri_mmcs() from configs

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* refactor(lmcs): unify MMCS types with const-generic salt parameter

This commit restructures the LMCS (Lifted Matrix Commitment Scheme) crate
to provide a cleaner API with unified hiding/non-hiding support through
const generics.

## Architectural Changes

### Type Renames and Reorganization
- Rename `MerkleTreeLmcs` → `LmcsMmcs` (clearer MMCS wrapper naming)
- Rename `MerkleTreeHidingLmcs` → `HidingLmcsMmcs`
- Rename `LiftedMerkleTree` → `LiftedHidingMerkleTree<F, D, M, DIGEST_ELEMS, SALT_ELEMS>`
- Add `LiftedMerkleTree` as type alias for `LiftedHidingMerkleTree<..., 0>`
- Extract MMCS trait implementations to new `mmcs.rs` module
- Delete `hiding_lmcs.rs` (functionality consolidated via SALT_ELEMS parameter)

### New Configuration Type
- Add `LmcsConfig<F, D, H, C, WIDTH, DIGEST, SALT>` struct
- Holds cryptographic primitives (sponge + compression) with const-generic SALT
- Provides `build_tree` and `build_tree_hiding` methods for convenient construction
- Includes `verify` method for unified multi-opening proof verification
- Compile-time assertions prevent misuse (SALT=0 for build_tree, SALT>0 for build_tree_hiding)

## Proof System Enhancements

### New Types
- `Opening<F, Salt>`: Per-query row data with optional salt
- `Proof<F, D, DIGEST_ELEMS, Salt>`: Unified multi-opening proof with openings + compact siblings

### API Additions
- `LiftedHidingMerkleTree::open_multi(&[usize]) -> Proof`: Multi-index opening
- `LiftedHidingMerkleTree::authentication_paths(&[usize])`: Batch path extraction

### Renames
- `MultiOpeningError` → `CompactProofError`

### Serialization Support
- Add `Serialize`/`Deserialize` derives to: `NodeIndex`, `CompactProof`, `Opening`, `Proof`

## Internal Improvements

- Parallelize leaf digest squeeze operation with `into_par_iter()`
- Add `compute_leaf_digest` helper shared by `LmcsConfig::verify` and MMCS `verify_batch`
- Change `salt()` return type from `Option<Vec<F>>` to `[F; SALT_ELEMS]` array
- Simplify trait bounds by moving `Copy + PartialEq` constraints to impl blocks
- Add serde bounds to all generic proof types

## Test Coverage

- `multi_opening_roundtrip`: Verify multi-index opening and verification
- `multi_opening_single_index`: Edge case for single index via multi-opening API
- `hiding_commit_open_verify_roundtrip`: Full hiding commitment flow with LmcsConfig
- `hiding_mmcs_roundtrip`: HidingLmcsMmcs MMCS trait verification
- `hiding_mmcs_different_salts_different_roots`: Different RNG seeds produce different commitments

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* refactor(lmcs): introduce Lmcs and LmcsTree traits for unified API

- Add `Lmcs` trait with `build_tree()` and `verify()` methods
- Add `LmcsTree` trait for tree operations (`root()`, `open_multi()`, etc.)
- `LmcsConfig` now takes packed types (PF, PD) directly as type parameters
- Add `HidingLmcsConfig` as separate type with internal RNG
- Implement `Mmcs` directly on config types, remove wrapper types
- Simplify proof module: replace CompactProof/NodeIndex with direct
  sibling collection in canonical order (left-to-right, bottom-to-top)
- Unify LiftedMerkleTree with const-generic SALT_ELEMS parameter

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* refactor(lifted): migrate from MMCS to LMCS with batch multi-opening

Replace p3_commit::Mmcs with Lmcs/LmcsTree traits from p3-miden-lmcs
throughout the lifted PCS implementation. This change:

- Adopts compact multi-opening proofs via tree.open_multi() instead of
  per-query Merkle openings, reducing proof size overhead
- Removes intermediate query proof types (DeepQuery, FriQuery, QueryProof)
  in favor of direct L::Proof vectors in the proof structure
- Simplifies DeepPoly to hold only computed evaluations, not matrix refs
- Simplifies error types by removing MmcsError generic parameter
- Moves p3-miden-lmcs from dev-dependency to regular dependency

The verifier now processes all query indices in batch, calling
lmcs.verify() once per commitment tree rather than per-query-index.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* fix(lifted): remove unnecessary clone on Copy types

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* fix(lifted): rename Fo/EFo to Base/Ext to avoid typo false positive

The typo checker flagged `Fo` as a potential misspelling.
Renamed to `Base`/`Ext` which is clearer and more descriptive.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* chore: remove unused dependencies

Remove dependencies flagged by cargo-machete:
- p3-miden-lifted: p3-miden-stateful-hasher, p3-symmetric, serde
- p3-miden-dev-utils: p3-util, paste

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* refactor(lmcs): rename Proof to BatchProof, add single-opening Proof type

- Rename `Proof` to `BatchProof` for multi-opening proofs with deduplicated siblings
- Add new `Proof` type for single-opening proofs with full authentication path
- Add `extract_proofs` method to extract individual `Proof`s from a `BatchProof`
- Rename `verify` to `open` on `BatchProof` for consistency
- Move `recompute_root_in_place` from free function to `BatchProof` method
- Add comprehensive tests for proof extraction and verification

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* refactor(lmcs,lifted): simplify API naming and consolidate tests

Naming:
- PcsConfig → PcsParams (clearer semantics)
- open_multi → prove_batch, verify → open_batch (prover proves, verifier opens)
- FRI: query → open_batch, open_queries → prove_queries

API:
- Replace Dimensions with widths + log_max_height parameters
- Reorder params: params first, then lmcs
- compute_root takes &Opening instead of separate rows + salt args

Code organization:
- Move BatchProof to batch_proof.rs, Opening to opening.rs
- proof.rs now only contains single-opening Proof type

Tests:
- Consolidate 7 unit tests into single parameterized recompute_root_cases
- Remove verbose docstrings that restated code

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* make work with periodic values over base field

* refactor(workspace): rename p3-miden-lifted to p3-miden-lifted-fri and hoist pcs to crate root

* fixup! refactor(workspace): rename p3-miden-lifted to p3-miden-lifted-fri and hoist pcs to crate root

* Add transcript crate docs and layout

* refactor: make lifted PCS/FRI/DEEP channel-first

Move lifted PCS/FRI/DEEP to a channel-only transcript flow so protocol
code never constructs proof structs and transcript transport becomes a
clean boundary. Transcript types are retained only as structured views
parsed from verifier channels for inspection/debugging.

Transcript transport
- add `TranscriptData` in `p3-miden-transcript` and export it
- add `ProverTranscript::{into_data,data}` and `VerifierTranscript::from_data`
  to move prover transcripts into verifier replays

DEEP
- introduce `DeepEvals` and `BatchedEvals` containers in `deep/evals.rs`
  to represent grouped evals and support point-major transcript IO
- remove `MatrixGroupEvals`; reuse `BatchedEvals` in interpolation/prover
- replace `DeepProof` with `DeepTranscript` parsed from verifier channels
- write evals + padding to channels, grind, and sample α/β via channels
- `DeepOracle::new` reads evals from channels and returns `(oracle, evals)`
- add `reduce_with_powers_from` for incremental reductions while streaming

FRI
- commit phase streams commitments, PoW witnesses, and final poly via channel
- replace `FriProof` with `FriTranscript`/`FriRoundTranscript` (view only)
- `FriOracle::new` reads per-round transcript data from verifier channels
- query proofs stream via channel; verifier reads openings from channel
- preserve round structure via `FriRoundOracle` and round-indexed errors
- add verifier-side structural check for query input lengths

PCS
- replace `Proof` with `PcsTranscript` (view only) + `OrderedProofs`
- rename APIs to `open_with_channel` / `verify_with_channel`
- `verify_with_channel` returns verified `DeepEvals` instead of cloning proof data
- parse LMCS openings from transcript hints when building `PcsTranscript`

LMCS
- refactor to channel-based openings and transcript hints
- new `LmcsConfig` in `lmcs.rs` and `HidingLmcsConfig` in `hiding_lmcs.rs`
- `Lmcs::open_batch` reads hints from a verifier channel
- `Lmcs::read_batch_from_channel` reconstructs per-index `Proof`s
- `Proof` now stores `rows`, `salt`, and `siblings` (no `Opening`)
- `LiftedMerkleTree` implements `LmcsTree` and streams hints via `prove_batch`
- add `single_proof` helper and `digest_rows_and_salt` utility
- update MMCS verification to use rows+salt+siblings and restore structural checks
- remove `batch_proof.rs` and `opening.rs`, simplify `LmcsError`
- refresh crate docs to describe transcript hint flow

Tests/benches
- update DEEP/FRI/PCS tests to round-trip via transcript data
- add LMCS tests for transcript-based open/read behavior and edge cases
- bench PCS by measuring `TranscriptData` size
- add `p3-miden-transcript` dependencies where needed

Misc
- update Poseidon2 config macro to accept a permutation type identifier
  and instantiate it with `WIDTH`
- refresh FRI folding docs to match the struct-based API

* refactor+docs(lmcs): move mmcs to separate module and document

* refactor(lmcs+fri): Align LMCS openings and simplify DEEP eval flow

- add LMCS alignment to tree/config APIs and document padding semantics
- centralize row/width alignment helpers and reuse in tests/tools
- simplify DEEP eval batching/reduction and remove alignment from params
- update FRI/PCS verifier/prover paths to use aligned widths and LMCS alignment

* Refactor LMCS batch proof parsing and storage

- add BatchProof/LeafOpening with map-keyed openings and sibling reconstruction helpers
- move transcript parsing to Lmcs::read_batch_proof_from_channel and update PCS transcript parsing
- remove SingleProof assoc type usage and return map-based single proofs from batch proofs
- update LMCS/MMCS tests and docs to use batch proof flow
- fix minor linting nit in MMCS verifier

* refactor(lmcs+fri): clean up

* docs(lmcs,fri): initial documentation

* Docs: clarify lifted PCS shift/constraints, log_max_height usage, and query expectations

* Make LMCS alignment private and safe

* Move README.md from old crate to p3-miden-lifted-fri

* fix: ensure SIMD packing is the same when constructing lifted tree.

* Clarify eval-point preconditions and refine FRI tests

* add test for small traces without FRI rounds or zero blowup

* update README.md

* Rename log_max_height to log_lde_height and clarify domain roles

* docs(lifted-fri): explain alignment padding semantics
  - test(fri): assert transcript fully consumed after verification

* Clarify FRI folding docs for folded value vs f(β)

* refactor(lmcs): unify hash naming and canonical batch parsing

- add `Lmcs::hash`/`Lmcs::compress` and route proof reconstruction + MMCS verification through them; remove the standalone digest helper
- generalize `Proof`/`BatchProof` over the commitment hash type and update tests accordingly
- canonicalize batch hint parsing/proving: coalesce duplicate indices in first-occurrence order, read openings once, enforce empty/out-of-range guards, and keep sibling hints in canonical order
- document duplicate-index behavior and padding semantics; align docs/SECURITY language to “hash” vs “commitment”
- import `VerifierChannel` in lifted-fri tests for transcript exhaustion checks

* fix(lmcs+lifted-fri): separate aligned vs unaligned openings and expand tests

- LMCS: make alignment an explicit tree choice (build_tree vs build_aligned_tree), tighten docs,
  and keep internal alignment builder crate-scoped
- Hiding LMCS: align tree construction API and document RNG/security expectations
- MMCS: clarify width semantics when alignment padding is present
- Lifted FRI: derive DEEP alignment from trace trees and treat FRI round openings as unaligned
- Tests: add multi-trace PCS roundtrip, cover FRI arities 2/4/8 in one loop, and add LMCS
  duplicate-index + alignment-mode checks

Test: make lint
Test: make test

* audit(lifted-fri+lmcs): document DEEP preconditions and expand FRI/MMCS tests

Summary:
- Document DEEP preconditions for evaluation points (distinct, outside `H` and `gK`) in module, prover, and verifier docs.
- Refactor FRI tests into table-driven roundtrips (arity 2/4/8 + blowup-0), and strengthen final‑polynomial correctness using a constructed polynomial `f(X)=g(X^(2^r))`.
- Consolidate MMCS negative tests into a single table-driven test that covers out-of-range indices, misordered `Dimensions`, unaligned dimensions, row length mismatches, siblings length errors, and root mismatch, with a baseline “valid proof” check.

Files changed:
- `p3-miden-lifted-fri/src/deep/mod.rs`
- `p3-miden-lifted-fri/src/deep/prover.rs`
- `p3-miden-lifted-fri/src/deep/verifier.rs`
- `p3-miden-lifted-fri/src/fri/tests.rs`
- `p3-miden-lmcs/src/mmcs/tests.rs`

Tests:
- `make lint`

* docs: update SECURITY.md

* prover: compact periodic LDE tables

* prover: drop unused periodic helper

* fix failing tests and add changelog entry

* fix lints

* address feedback

* fix(docs)

* docs: improve SECURITY.md and README.md

* refactor(transcript): replace Option with TranscriptError across verifier APIs

Introduces TranscriptError enum with explicit variants (NoMoreFields,
NoMoreCommitments, InvalidGrinding) for better error diagnostics. Removes
redundant defensive checks in BatchProof (index bounds, empty indices)
since indices are trusted from Fiat-Shamir; invalid indices now produce
proofs that fail verification rather than early errors.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* test: fix lmcs parsing test

* refactor(deep+fri):
- simplify evals.rs
- add comments for deep/prover.rs
- simplify fri verifier

* refactor(lmcs+fri): use sorted tree indices and BTreeMap for deterministic transcript order

- Change `open_batch` to return `OpenedRows` (BTreeMap<usize, Vec<Vec<F>>>) instead of Vec
- Change `prove_batch` and `open_batch` to accept `impl IntoIterator<Item = usize>`
- Use BTreeSet for tree indices throughout prover/verifier to ensure sorted order
- Convert FRI verifier to use BTreeMap for tracking evals through folding rounds

Documentation fixes:
- Fix "input order" / "first-occurrence order" → "sorted tree index order" in docstrings
- Add comment explaining transcript determinism requires sorted order
- Update README.md: add missing crates (lmcs, transcript), fix p3-miden-symmetric → p3-miden-stateful-hasher
- Add inline math comments for bit-reversal indexing in FRI/DEEP verifiers

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

* docs(fri): document soundness during ldt

* address reviews

* refactor(fri+lmcs): address PR review comments

Naming & clarity in FRI prover:
- Rename `num_rows`/`log_num_rows` to `folded_domain_size`/`log_folded_domain_size`
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2762600896
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2762627912
- Define ω in the algorithm overview and ω_arity in the coset structure section
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2762570298
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2762581218
- Make range of coset evaluations explicit: [y₀, ..., y_{arity-1}]
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2762574984
- Explain why FRI round commitments use `build_tree` (unaligned)
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2762635835
- Fix fold comment wording: "interpolate coset evaluations and evaluate at β"
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2762645173
- Complete the sentence about bit-reversed order
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2762649066
- Define L = log(folded_domain_size) in the s_inv update comment
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2762663155
- Clarify final polynomial degree is strictly less than final_poly_degree
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2762667158
- Restructure loop to use single `mut domain_size` with per-iteration
  `let folded_domain_size` for clarity

Rename proof-of-work fields to name what they guard:
- `FriParams.proof_of_work_bits` → `folding_pow_bits`
- `DeepParams.proof_of_work_bits` → `deep_pow_bits`
- `PcsParams.query_proof_of_work_bits` → `query_pow_bits`
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2762641752

FRI verifier:
- Rename `log_num_rows` → `log_folded_domain_size`
- Fix docstring: `initial_evals` → `evals` to match parameter name
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2762724108
- Use `.get()` instead of direct indexing on `opened_rows` with `FriError::MissingRow`
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2768593017

Documentation fixes:
- Fix DEEP acronym: "Domain Extension for Eliminating Pretenders"
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2762515361
- Elaborate on adjacent negation property in bit-reversed order
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2763150775
- README: better description, merge redundant bullet points
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2763426304
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2763433236

LMCS fixes:
- Use "digest" instead of "hash word" in lifted_tree.rs
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2758731163
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2758731965
- Remove confusing "unless the caller checks them" clause
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2758761928
- Fix cut-off sentence in lmcs.rs docstring
  https://github.com/0xMiden/p3-miden/pull/10#discussion_r2758562871

* docs+test(fri+lmcs): address PR #10 review comments

Document the Horner/RLC convention across the DEEP module, improve
README wording, clarify responsibility boundaries, and add test cases.

Documentation:
- Expand horner/horner_acc docstrings with evaluation semantics (utils.rs)
- Add "Random Linear Combination Convention" section (deep/mod.rs)
- Expand negated-coefficient comment with full derivation (deep/prover.rs)
- Document Horner accumulation ordering in open_batch (deep/verifier.rs)
- Clarify alignment padding is caller/AIR responsibility (lib.rs)
- Document transcript consumption caller duty (verifier.rs)

README fixes:
- "two points" -> "N points (typically N=2)" (lifted-fri README)
- "shared max" -> "shared maximal height" (lmcs README)
- "canonical sibling emission" -> "canonical sibling ordering in proofs"
- Attribute height heterogeneity to multi-AIR designs
- Clarify max height scope to "same commitment group"
- Add explicit matrix absorption ordering note

Tests:
- Extract test_params() and run_pcs_case() helpers
- Consolidate PCS tests into case-driven test_pcs_cases
- Add mixed-height roundtrip case (LMCS upsampling)
- Add high-degree rejection case (FRI soundness)

Addresses:
- https://github.com/0xMiden/p3-miden/pull/10#discussion_r2757798696
- https://github.com/0xMiden/p3-miden/pull/10#discussion_r2757962287
- https://github.com/0xMiden/p3-miden/pull/10#discussion_r2762532017
- https://github.com/0xMiden/p3-miden/pull/10#discussion_r2763362340
- https://github.com/0xMiden/p3-miden/pull/10#discussion_r2763430030
- https://github.com/0xMiden/p3-miden/pull/10#discussion_r2763459226
- https://github.com/0xMiden/p3-miden/pull/10#discussion_r2763464092
- https://github.com/0xMiden/p3-miden/pull/10#discussion_r2763472751
- https://github.com/0xMiden/p3-miden/pull/10#discussion_r2763481898
- https://github.com/0xMiden/p3-miden/pull/10#discussion_r2763487592
- https://github.com/0xMiden/p3-miden/pull/10#discussion_r2767845484

* refactor(deep+fri+lmcs): harden verifiers, fix bit-reversal, add strict transcript check

Address remaining PR #10 review comments and harden the verification stack.

Bug fixes:
- Fix bit-reversal mismatch in PcsTranscript parser (#A): apply
  reverse_bits_len to sampled exponents, rename indices -> tree_indices
- Fix opened_rows panic in DEEP verifier: replace indexing with .get()
  + DeepError::InvalidOpening (huitseeker panic nit, DEEP side)

New features:
- Add verify_with_channel_strict (#15): rejects trailing transcript
  data with PcsError::TrailingData
- Add VerifierChannel::receive_hint_field_array: replaces
  receive_hint_field_slice + try_into().unwrap() pattern
- Add EvalPointOnDomain defensive check in DEEP quotient computation

Notation and doc fixes:
- Correct RLC notation from ai to aW-1-i throughout deep/ (#2)
- Inline reduce_point into DeepOracle::new, remove from evals.rs
- Clarify Alignable::Target doc for field-native sponges (#4)
- Add "(e.g., STIR or WHIR)" to LMCS README (#12)
- Document zero-queries failure path on test_low_degree (#D)
- Mark all read_from_channel / from_verifier_channel as parse-only
- Improve inline comments for alignment and eval representation (#1, #2)

Error improvements:
- FRI: remove InvalidProofStructure, rename MissingRow -> InvalidOpening,
  add round/tree_index to all variants
- DEEP: LmcsError now carries { source, tree }, add InvalidOpening
- All error variants carry structural coordinates, not field values

Tests:
- Add batch_proof_consistent_with_open_batch (lmcs/proof.rs)
- Make roundtrip_open_batch pub for cross-module reuse

Addresses: #1, #2, #4, #12, #15, #A, #D, plus huitseeker panic nit

* fix(lifted-fri): clippy get_first lint and broken rustdoc links

- fri/verifier.rs: use .first() instead of .get(0), chain .and_then calls
- deep/mod.rs: replace intra-doc links to pub(crate) types with code backticks
- fri/proof.rs: replace doc link to private FriOracle::test_low_degree with code text

* refactor(deep): replace try_fold with explicit loop in DEEP quotient evaluation

* refactor(fri): store final polynomial in descending degree order for Horner eval

Reverse the final polynomial coefficients at the prover before writing
to the transcript, so they are stored as [cₙ, ..., c₁, c₀]. This
lets the verifier evaluate via Horner directly without reversing the
iterator at each query point.

* feat(lmcs,lifted-fri): add tracing spans for profiling

Add tracing instrumentation to LMCS and lifted FRI, following the
same patterns used in p3-miden-prover and p3-miden-fri.

LMCS (p3-miden-lmcs):
- info_span "hash leaves" around leaf state building + squeeze
- debug_span "compress tree layers" around Merkle tree compression

Lifted FRI (p3-miden-lifted-fri):
- #[instrument] "PCS opening" on open_with_channel
- info_span "DEEP quotient" around DEEP quotient construction
- info_span "evaluate at OOD points" around barycentric evaluation
- info_span "FRI commit phase" around FRI folding rounds
- debug_span "idft final poly" around final polynomial IDFT
- info_span "query phase" around query proof generation

https://claude.ai/code/session_0194A5EedbvVHoKpBmtSr9xb

* address feedback

* factor out table period computation

* feat(lifted-fri): add tracing spans and PCS profiling benchmark

- Add tracing debug_span instrumentation to PointQuotients::new,
  batch_eval_lifted, and barycentric_weights computation
- Add pcs_trace benchmark for profiling lifted PCS open with
  tracing-subscriber (Goldilocks + Poseidon2, arity-4)
- Add tracing-subscriber workspace dependency
- Add debug_assert for ascending height invariant in accumulate_matrices
- Rename shadowed variable widths -> round_widths for clarity in proof.rs

* refactor(lmcs,deep): introduce RowList<T> for flat variable-width row storage

Replace Vec<Vec<F>> with RowList<T> in LMCS proof structures and opened
rows (Proof, LeafOpening, OpenedRows, LmcsTree::rows). RowList stores
all elements contiguously with a separate widths vector, eliminating
N+1 heap allocations per opening and enabling flat iteration.

In the DEEP subsystem, restructure DeepEvals from a group-major
Vec<Vec<RowMajorMatrix<EF>>> to a point-major Vec<RowList<EF>>,
matching the verifier's per-point Horner reduction access pattern.
Replace BatchedEvals/BatchedGroupEvals with RowList<FieldArray<EF, N>>
in the prover and interpolation code.

Other changes:

- Replace materializing aligned() with lazy iter_aligned(), avoiding
  a full padded copy during OOD transcript writes and Horner reduction
- Simplify channel reads from per-width loops to single bulk
  receive_algebra_slice / receive_hint_field_slice calls
- Move trait bound off DeepEvals struct definition onto impl block
- Add inline comments explaining STARK protocol context (Fiat-Shamir
  binding, DEEP soundness, FRI proximity argument, sponge alignment)

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* fix: Replace verifier panics with proper error returns (#19)

* fix: Replace verifier panics with proper error returns

Replace assert_eq! calls in verifier with proper error handling
to prevent DoS attacks on verification APIs:

- process_preprocessed_trace: Return InvalidProofShape instead of
  panicking when ZK is enabled with preprocessed trace
- process_preprocessed_trace: Return InvalidProofShape instead of
  panicking on height mismatch
- bus_multiset_boundary_varlen: Add bounds check for row length
  and return Result
- bus_logup_boundary_varlen: Add bounds check for row length
  and return Result
- air_wrapper_bus_boundary: Iterate only over valid indices to
  avoid OOB access on aux arrays

Fixes #18

* chore: Changelog

* fix(deep,fri,lmcs): address remaining PR review comments

- deep/prover: fall back to scalar path when packing width exceeds domain size
- deep/proof, fri/proof: clarify that PoW is verified during transcript parsing
- deep/verifier: use 'codeword' instead of 'polynomial', 'verification failure'
  instead of 'spurious rejections'
- fri/verifier: use 'folded query point' instead of 'remaining query point'
- lmcs/utils: clarify RowList docstring re: verifier LDT queries
- lmcs/README: expand absorption order mechanics
- lifted-fri/README: clarify N is fully generic, document lifted-trace soundness
  approach

* Fix aux boundary constraints and add test (#22)

* Fix aux boundary constraints and add test

* chore: Changelog

* feat: lifted STARK prover/verifier with multi-height trace support

Add p3-miden-lifted-{air,stark,prover,verifier} crates and
p3-miden-lifted-examples with benchmark binaries.

## New Crates

| Crate | Purpose |
|---|---|
| p3-miden-lifted-air | AIR traits (LiftedAir, LiftedAirBuilder, PeriodicAirBuilder) + symbolic analysis |
| p3-miden-lifted-stark | Shared types: LiftedCoset, Selectors, AirWitness, AirInstance, config |
| p3-miden-lifted-prover | Lifted STARK prover with SIMD constraint evaluation |
| p3-miden-lifted-verifier | Lifted STARK verifier with OOD quotient reconstruction |
| p3-miden-lifted-examples | Benchmark binaries (Keccak, Blake3, Poseidon2, Miden dummy AIR) |

## Development History (squashed from 36 commits)

### Phase 1: Initial Scaffolding (Jan 29–30)

- ef8eb39 feat(lifted-stark): initial commit
- 0d74593 feat(lifted-stark): fix compilation
- 4cbece1 fix(lifted-stark): validate aux traces and align base/EF conversions
- 9792a10 feat(lifted): add LDE/LMCS helpers and refine transcript/layout plumbing
  - p3-miden-lifted-fri::lde with nested-coset LDE helpers and LMCS commit helper
  - Rework periodic column handling for polynomial-coefficient encoding via naive DFT
  - Group trace/aux widths into AirWidths vector; serialize in layout snapshot
  - Cache aux traces once in prover, reuse for commitment + numerator LDEs

### Phase 2: Architecture Refactoring (Feb 2–5)

- 00384e1 refactor(transcript+lifted): add init transcript and propagate transcript errors
- 59fce7c refactor(lifted-stark): reorganize modules and remove dead code
  - Move periodic LDE handling to prover/verifier crates
  - Add commit.rs for trace commitment helpers
  - Add constraints.rs consolidating constraint evaluation
  - Remove unused layout.rs, selectors.rs, transcript.rs
- 48968a2 refactor(lifted-stark): centralize domain ops in LiftedCoset and separate prover/verifier
  - LiftedCoset abstraction with selector/vanishing computation
  - Selectors<T> container generic over Vec<F> (prover) and EF (verifier)
  - Split ConstraintFolder: SIMD ProverConstraintFolder vs EF-only verifier folder
  - prove_multi with cyclic extension and beta-folding for multi-trace support

### Phase 3: SIMD & Performance (Feb 7–12)

- a777450 refactor(lifted-stark): SIMD constraint evaluation, Horner folding, and API cleanup
  - PackedField/PackedExt for SIMD-parallel evaluation (WIDTH points per iteration)
  - Horner folding replacing pre-computed alpha powers
  - LiftedCoset constructor: new(log_trace, log_blowup, log_max_trace)
  - Unify prove_single as thin wrapper around prove_multi
  - Optimize quotient: flatten EF to base field before DFT
  - Bitmask cyclic extension instead of heap-allocating
- 1510d96 perf(lifted-prover): collect-then-combine constraint accumulation with SIMD dot products
  - ConstraintType, ConstraintLayout with decompose_alpha() in lifted-air
  - ProverConstraintFolder collects into base/ext constraint vectors
  - finalize_constraints() combines via PackedField::packed_linear_combination
- a3a4a79 refactor(lifted-prover): in-place constraint accumulation and vanishing division
  - evaluate_constraints_into takes &mut [EF] output slice
  - Fuse beta-folding into main loop
  - divide_by_vanishing operates in-place

### Phase 4: Lifted AIR Crate (Feb 10–11)

- 1191909 refactor(lifted-stark): introduce p3-miden-lifted-air crate
  - LiftedAir<F, EF> super-trait: num_randomness, aux_width, build_aux_trace, eval
  - LiftedAirBuilder super-trait inheriting upstream traits + aux_values()
  - Symbolic module from upstream 0xMiden/Plonky3 periodic-air-builder branch
- 4b34844 feat(lifted-air): infer constraint degree from symbolic AIR analysis

### Phase 5: Shared Types & Validation (Feb 10)

- 6da63c4 refactor(lifted-stark): shared AirWitness/AirInstance types
  - AirWitness: prover witness (trace + public values), validates power-of-two
  - AirInstance: verifier instance (log height + public values), Copy
  - Fully Result-based validation (no panics for bad input)

### Phase 6: Examples & Benchmarks (Feb 16–19)

- 9b19511 feat(examples): add lifted-examples crate with benchmark binaries
- 69434b3 fix(deep): slice SIMD coeffs to matrix width, add N>0 assertions, expand benchmarks
- a26fa16 feat: make aux traces optional; add Blake3/Poseidon2 AIR wrappers and 3-hash benchmarks
- b6a5501 feat(examples): add StatsLayer for multi-iteration benchmarking
- 1d7dddd feat(examples): add Miden dummy AIR benchmarks
- ebadc58 feat(examples): add proof size measurement via serde SizeCounter

### Phase 7: DEEP Optimizations (Feb 18)

- a20ad5c perf(deep): fuse column reduction + quotient assembly
- 1cc41ea/b268283 refactor then revert: OOD openings slice-based (no improvement)

### Phase 8: Documentation & Cleanup (Feb 9–23)

- 46bac65 docs(lifted-stark): add README, fix quotient_domain
- e8c62eb docs: promote notes.md to README.md and include as crate-level rustdoc
- 621ecbb docs(prover,verifier): document Fiat-Shamir binding and transcript boundaries
- 8aaa622 refactor: re-export internal sub-crate types from prover/verifier; fix unused deps
- a4cd8e4 refactor(lifted-prover): extract quotient.rs module for quotient helpers

### Minor Fixes

- 28145ca fix(periodic): store Option<RowMajorMatrix> to avoid width-0 UB
- 44baabe refactor(periodic): PeriodicLde::build returns Self, panics on invalid input
- 4707ff4 fix(docs): fix broken rustdoc links in lifted-air and lifted-prover
- fddc5c0 fix(examples): resolve doc link warnings and remove unused Default impl
- 7396d3c cleanup(lifted-prover): remove redundant assert format args
- eb55aa6 cleanup: simplify error variants and use is_multiple_of
- 506efe2 feat(lifted-prover): add tracing spans for profiling
- 87d7011 feat(lifted-fri): improve tracing granularity for prover profiling

* CHANGELOG.md

* chore(lifted-fri): clean up

* feat(lifted-start): add proof transcript

* bump Plonky3 deps

* revert LMCS commitment type

* feat(transcript): derive Deserialize for TranscriptData

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* docs: expand lifted-fri and lmcs READMEs

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* fix(ci): remove unused dependency

* fix(lmcs): do not absorb empty salt

The stateful hasher semantics do not guarantee that absorbing an empty slice is a no-op (it is for the stateful sponge) which led to failing Merkle proof verification

* refactor(verifier): clean up OOD eval access and fix alignment padding

Verifier was using iterator-based pre-collection to access opened
evaluations, then manually truncating with .take(width). This was
verbose and error-prone when the sponge rate alignment is not a
multiple of EF::DIMENSION — the old code could pass misaligned
padding into row_to_packed_ext.

Simplify by slicing opened rows directly via row(j)[..width],
which cleanly strips alignment padding at the point of use.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* bump to latest

* docs(lifted): improve documentation

* docs(prover): address PR review comments on quotient docs

- Fix gJ description: it is a coset subset of gK, not a subgroup
- Clarify fused scaling trick: explain it collapses D coset-iDFT/DFT
  pairs into one plain iDFT + diagonal scale + one plain DFT
- Explain zero-padding: dft_batch expects full buffer unlike
  coset_lde_batch which pads internally

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* docs(quotient): document zero-pad perf gap and upstream DFT trait improvement

The quotient commitment zero-pads N→N·B rows before a full-size DFT,
which processes zero rows through every butterfly stage (~9% overhead
for B=4). Document that dft_batch/coset_dft_batch need an added_bits
parameter to evaluate degree-<N coefficients on a larger domain,
matching what Radix2DftParallel::coset_lde_batch already does
internally after its iDFT phase.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* refactor: rename `zeta` to `z` for OOD evaluation point

Consistently use `z` (and `z_next`) instead of `zeta` across all crates,
code, doc comments, and markdown documentation. This aligns variable
naming with the mathematical convention used in comments and formulas.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* refactor: apply PR review fixes across lifted STARK crates

- LMCS: move empty-indices check before loop in open_batch
- LMCS: document salt read no-op for SALT_ELEMS == 0
- Verifier: use PublicVar = F (matches prover's ConstraintFolder)
- Verifier: evaluate periodic polys at (max_trace_height, z) instead
  of computing y_j per instance
- Verifier: add transcript consumption check in StarkTranscript
- LiftedCoset: inline lifting into selectors_at, remove selectors_at_ood
- LiftedCoset: add vanishing_at, remove unused inv_vanishing_at
- DEEP: safe zero-copy flatten via FieldArray::as_raw_slice + as_flattened,
  document reconstitute_from_base safety preconditions

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* refactor: weaken trait bounds on STARK prove/verify APIs

- Remove `Commitment: Copy` from `ProverChannel` and `VerifierChannel`
  traits, weakening to `Clone`. All internal usages (observe_slice,
  extend_from_slice) only need Clone. Dereference sites changed from
  `*channel.receive_commitment()?` to `.clone()`.

- Remove `L::Commitment: Copy` from all prove/verify function bounds.

- Remove `Dft: TwoAdicSubgroupDft<F>` from verifier bounds — the
  verifier never calls `config.dft` (DFT is prover-only for LDE).

- Remove cargo-culted `PrimeField64` and `PrimeCharacteristicRing`
  bounds from prover and verifier — none of `as_canonical_u64`,
  `ORDER_U64`, or `PrimeCharacteristicRing` methods are used.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* refactor: make StarkConfig a trait and strengthen Algebra bounds

Cherry-pick two standalone improvements from the lifted-stark-aux branch:

1. Local ExtensionBuilder/PermutationAirBuilder traits with Algebra<Expr>
   bound (stronger than From<Expr>), enabling full arithmetic interop
   between base and extension field symbolic expressions.

2. StarkConfig as a trait with GenericStarkConfig concrete impl, bundling
   Lmcs/Dft/Challenger as associated types. Eliminates turbofish at all
   prove/verify call sites.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* refactor: add Channel abstraction for prover and verifier

Introduce a `Channel` trait in `p3-miden-transcript` that unifies the
prover and verifier transcript interfaces behind a common API for
`observe`, `hint`, and `consume` operations. This simplifies generic
code that needs to work with either side of the Fiat-Shamir channel.

Also extracts shared helper utilities into `p3-miden-lifted-stark::util`
and streamlines proof deserialization in the verifier.

Based on the design from PR #33.

Co-Authored-By: Robin Salen <salenrobin@gmail.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* refactor: centralize LMCS alignment in verify_aligned

Replace DeepEvals with plain OpenedValues<EF> (= Vec<Vec<RowMajorMatrix<EF>>>)
and add a verify_aligned entry point that handles width alignment and
truncation internally. The STARK verifier now passes original (unpadded)
widths and receives already-truncated matrices, removing scattered
aligned_widths calls and manual column slicing from the caller.

Also rename verify_with_channel → verify / verify_with_channel_strict →
verify_strict, and delete the DeepEvals wrapper (deep/evals.rs) in
favour of the standard RowMajorMatrix return type.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* bump with latest P3

* refactor: remove extension.rs module and reuse upstream one

* refactor: use Iterator::chain method instead of core::iter::chain free fn

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* fix: upgrade soundness-critical debug_assert to assert in public APIs

LiftedCoset::new and upsample_matrix are public functions whose
invariants (trace height ordering, power-of-two heights) guard
against silent corruption in release builds. debug_assert is
stripped in release mode, so these checks must be full asserts.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* Add lifted multi-trace aux alignment tests

* bump

* cleanup

* clippy

* fix error message

* remove PeriodicAirBuilder

* update CHANGELOG

* minor

* refactor(air): decouple aux trace building from AIR trait

Replace `LiftedAir::build_aux_trace` with a separate `AuxBuilder` trait
passed to the prover per instance, and decouple aux values from aux
column count. Add cross-AIR bus identity checking via
`LiftedAir::reduced_aux_values` with `ReducedAuxValues { prod, sum }`.

This makes the protocol less prescriptive about how auxiliary values are
produced and constrained, allowing more flexible bus batching strategies
(e.g. single running-sum column with inverse columns for logup).

- Add `aux` module: `AuxBuilder`, `EmptyAuxBuilder`, `ReducedAuxValues`
- Add `VarLenPublicInputs` for verifier-side per-bus public inputs
- Add `LiftedAirBuilder::aux_values()` and `Entry::AuxValue`
- Move instance types (`AirWitness`, `AirInstance`) to lifted-air crate
- Plumb aux values through prover/verifier constraint evaluation
- Add `bus_test.rs` end-to-end test for multiset + logup buses

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

� Conflicts:
�	p3-miden-lifted-verifier/src/verifier.rs

* refactor(air): flatten VarLenPublicInputs and make reduction fallible

- Flatten VarLenPublicInputs from &[&[&[F]]] to &[&[F]], moving bus-level
  grouping from protocol concern to AIR concern
- Add var_len_public_inputs to AirWitness (prover witness), propagate
  through to_instance()
- Add num_var_len_public_inputs() to LiftedAir trait
- Make reduced_aux_values() return Result<_, ReductionError> where
  ReductionError is a Box<dyn Error + Send + Sync> type alias
- Add VerifierError::Reduction variant with direct pass-through
- Document Fiat-Shamir commitment requirement for var_len_public_inputs
- Add bus_wrong_input_count_fails test exercising fallible reduction

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* refactor: make aux trace mandatory for all LiftedAir instances

Remove default implementations from `num_randomness()`, `aux_width()`,
and `num_aux_values()` on the `LiftedAir` trait, making them required.
Remove all `Option` wrappers and `has_aux` conditional branching from
the prover and verifier. Hash AIRs (keccak, blake3, poseidon2) now
declare a minimal 1-column dummy aux, with `DummyAuxBuilder` in the
examples crate producing the zero trace.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* fix(ci): rename `aux` module to `auxiliary` to fix Windows checkout

`aux` is a reserved device name on Windows (alongside CON, PRN, NUL,
etc.), causing `git checkout` to fail with "invalid path" on Windows CI
runners before any code can compile.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* docs: add changelog entry for aux trace refactor

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* fix(proof): receive aux values in StarkTranscript to match verifier

StarkTranscript::from_verifier_channel was missing the aux values
receive step between the aux commitment and alpha/beta sampling,
causing a transcript mismatch with verify_multi. Added the
all_aux_values field and receive calls, and documented why aligned
widths are needed for PCS transcript parsing.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* fix: address remaining PR review comments

- Rename "scalars" to "values"/"elements" in aux-related docs
- Add doc comments on Algebra impls for SymbolicExpression
- Clarify ExprEF bound: Algebra<Expr> for mixed arithmetic,
  Algebra<EF> for extension-field constants
- Validate var-len public inputs count in prover (new
  VarLenPublicInputsMismatch error variant)
- Update num_var_len_public_inputs doc to note prover validation

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* fix: address review comments and fix multi_aux_alignment test

- Update expression.rs doc to note algebra over any algebraic extension
- Document var-len public input validation in LiftedAir trait
- Update multi_aux_alignment test for AuxBuilder refactor

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* refactor: add lightweight ConstraintLayoutBuilder and reorganize constraints module

Move constraint layout discovery from the AIR crate to the prover crate
since it's only used there. Replace the heavy SymbolicAirBuilder-based
get_constraint_layout (which built Arc<SymbolicExpression> AST trees) with
a lightweight ConstraintLayoutBuilder that uses concrete field zeros —
no symbolic expressions, no degree tracking, no Arc allocations.

Also split the monolithic constraints.rs into a constraints/ folder:
- mod.rs: evaluate_constraints_into (parallel quotient domain evaluation)
- folder.rs: ProverConstraintFolder, finalize_constraints, batched helpers
- layout.rs: ConstraintLayout, ConstraintLayoutBuilder, get_constraint_layout

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* refactor(air): fork p3-air as p3-air-next and unify AIR trait hierarchy

Introduce p3-air-next, a local fork of Plonky3's p3-air that merges
PublicVar/preprocessed into AirBuilder and adds PermutationVal +
permutation_values() to PermutationAirBuilder. This eliminates the
need for lifted-air's parallel symbolic module.

Key changes:
- Add p3-air-next with extended AirBuilder (PublicVar, preprocessed),
  PermutationAirBuilder (PermutationVal, permutation_values), and
  PermutationValue variant in ExtEntry for symbolic analysis
- Delete p3-miden-lifted-air/src/symbolic/ — re-export fork's symbolic
  types instead of maintaining a separate copy
- Delete p3-miden-lifted-air/src/extension.rs — ExtensionBuilder now
  comes from the fork
- Simplify LiftedAirBuilder to a blanket impl over component traits
- Rename aux_values → permutation_values throughout prover/verifier
- Add UpstreamCompat adapter for crates.io AIR delegation in examples
- Remove BaseAirWithPublicValues (merged into BaseAir in the fork)

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* fix: remove unused tracing dependency from p3-miden-lifted-air

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* refactor(air): add validation helpers and improve error handling

Introduce `LiftedAir::validate()` and `AirInstance::validate()` to
check AIR properties and instance dimensions before proving/verifying.
Add `is_valid_builder()` to guard `eval()` against dimension mismatches.

Unify the old `ValidationError` into a richer `AirValidationError` with
per-check variants and make `validate_instances()` AIR-aware by taking
`(air, instance)` pairs. Add constraint-degree-vs-blowup checks to
both prover and verifier.

Document the three-tier trust model (trusted AIR, validated instance,
untrusted proof) in the `p3-miden-lifted-stark` module docs.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* docs: expand validate() docstring per review feedback

Co-Authore…
* Bump toolchain and refresh rand lockfiles

* ci: remove toolchain override for cargo msrv
* perf: make some operations for Goldilocks faster

* chore: update CHANGELOG.md

* apply review

* chore: address review nits after rebasing

---------

Co-authored-by: François Garillot <francois@garillot.net>
#961)

* ci: trim nextest matrix and cache rust builds

The nextest jobs spend most of their time compiling, not running tests. Local runs were 94.28s cold / 2.43s warm for default, 28.84s / 1.25s for no-std, and 137.33s / 0.77s for large-smt. Restoring rust-cache lets CI reuse those artifacts instead of rebuilding them from scratch.

The nightly nextest rows did not cover extra behavior. Recent CI runs on April 13, 2026 took almost the same time on stable and nightly, and the test targets do not rely on unstable Rust features. Keeping the stable lane preserves coverage while cutting duplicate work.

The large-smt filter was also stale. It matched merkle::smt::full::large, but the real tests live under merkle::smt::large. This change moves those tests into the large-smt lane, keeps the split disjoint, and updates the Makefile text to match what the target runs.

* ci: move heavy nextest jobs to WarpBuild

The longest test jobs are compile-bound, so they get the biggest payoff from a faster runner and the matching WarpBuild Rust cache. Local runs were 94.28s cold / 2.43s warm for default, 28.84s / 1.25s for no-std, and 137.33s / 0.77s for large-smt.

This keeps the change small. Only the main test matrix and the concurrent SMT nextest job move to warp-ubuntu-latest-x64-4x with WarpBuilds/rust-cache@v2. The rest of CI stays as it is.
* chore(clippy): add curated lint set and fix violations

* fix: opt in to unused-qualifications
Decouple log trace heights from AirInstance, carrying them instead in
StarkProof where they are observed into the Fiat-Shamir challenger
before the transcript begins. This makes the protocol identity depend
on the heights without requiring the verifier to know them a priori.

AirInstance now holds only public_values and var_len_public_inputs.
The instance module moves from miden-lifted-air to miden-lifted-stark,
since it now depends on protocol-level concerns (StarkProof).

Validation is refactored into validate_inputs() which takes instances
and log_trace_heights as separate arguments. AirWitness::to_instance()
is simplified (no longer fallible). verify_single no longer takes
log_trace_height as a parameter - it is read from the proof.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
The AirInstance / validate_instances symbols no longer exist in
miden-lifted-air; their doc references needed to be rewritten.
Also drop a redundant explicit link target in instance.rs.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Address review feedback on #956:

- Replace the instance/height count `assert_eq!` with a
  `HeightCountMismatch` error variant so malformed proofs surface as
  `VerifierError::Instance` instead of panicking the verifier process.
- Bound each `log_h ≤ MAX_LOG_DOMAIN_SIZE` before `1usize << log_h` and
  `two_adic_generator(log_h)`, returning `LogHeightTooLarge`.
- Introduce `InstanceShapes` to own the per-instance shape metadata
  previously stored as a loose `Vec<u8>` on `StarkProof`, with a shared
  `observe()` helper used by the prover, verifier, and
  `StarkTranscript::from_proof` so the Fiat-Shamir encoding is centralized.
- Include `instance_shapes.size_in_bytes()` in `StarkProof::size_in_bytes`
  so the lifted bench doesn't undercount proof size.
- Split `AirValidationError` into structural errors (`AirStructureError`,
  intrinsic to an AIR, lives in `miden-lifted-air`) and
  `InstanceValidationError` (instance/protocol-level, lives in
  `miden-lifted-stark::instance`).
- Derive `Debug` on `AirInstance`, `AirWitness`, and `InstanceShapes`;
  add a manual `Debug` impl for `StarkProof` under a
  `Commitment: Debug` bound.
- Update verifier module docs to reflect that `InstanceShapes` is the
  one statement component observed internally (callers must not
  pre-observe).

Adds tests covering the new malformed-proof paths: count mismatch,
oversized log heights, and non-power-of-two trace heights in the prover.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
…nd add Debug for StarkOutput

Address further review on #956:

- Restore `Serialize` / `Deserialize` on `StarkProof` and `InstanceShapes`
  (lost when `StarkProof` stopped being a type alias for `TranscriptData`).
  `StarkProof` routes the serde bounds through `TranscriptData<F, Commitment>`
  so the derive does not require `SC: Serialize`.
- Add a manual `Debug` impl for `StarkOutput` mirroring the `StarkProof`
  pattern (bounded on `StarkDigest` and `Commitment` rather than `SC`).
- Tighten the CHANGELOG entry to describe the migration without the
  incorrect miden-vm#2550 reference.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
… bound

Make StarkProof fields pub(crate) and expose wire-format summaries via
accessors (num_traces, num_field_elements, num_commitments). Read
per-instance log trace heights by parsing with StarkTranscript::from_proof,
which now carries the shape metadata on the returned transcript.

Replace the MAX_LOG_DOMAIN_SIZE guard with log_h + log_blowup <= TWO_ADICITY
so the check matches the actual downstream two_adic_generator call on the
LDE domain. Validate before observing into the challenger, so a rejected
shape never contaminates the Fiat-Shamir state.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
…ffer

Sample and discard an extension-field challenge right after observing the
instance shapes in both prover and verifier (and in StarkTranscript::from_proof),
so that subsequent Fiat-Shamir challenges commit to all previously absorbed
inputs regardless of sponge state. Exposed as `instance_challenge` on
`StarkTranscript` for visibility.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
…ng TODOs

Strip "currently" and TODO(#941) forward-looking references from user-facing
docs, fix stale `validate_instances` / `miden_lifted_air::AirWitness` paths
left over from the instance-module move, correct the `src/verifier/proof.rs`
entry in the modules table, and reframe the verifier multi-trace ordering
contract as "match the prover's order" rather than "protocol requires
ascending" — ascending is a prover-side cyclic-extension constraint, not a
verifier requirement.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
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.

6 participants