Skip to content

perf: reduce allocations in Poseidon hash functions#1129

Open
VolodymyrBg wants to merge 1 commit into
lambdaclass:mainfrom
VolodymyrBg:perf/poseidon-hash-allocs
Open

perf: reduce allocations in Poseidon hash functions#1129
VolodymyrBg wants to merge 1 commit into
lambdaclass:mainfrom
VolodymyrBg:perf/poseidon-hash-allocs

Conversation

@VolodymyrBg
Copy link
Copy Markdown

Description

Before these changes, Poseidon::hash and hash_single always allocated a Vec of length 3 for the state, and hash_many allocated a new Vec (block_state) for every processed block and copied the tail of the state on each iteration. This led to unnecessary heap allocations and extra copying in hot paths (especially for Merkle trees using hash_many), without providing any semantic benefit.

Type of change

Please delete options that are not relevant.

  • Optimization

Checklist

  • This change is an Optimization
    • Benchmarks added/run

@VolodymyrBg VolodymyrBg requested a review from a team as a code owner February 3, 2026 14:48
@VolodymyrBg
Copy link
Copy Markdown
Author

VolodymyrBg commented Feb 3, 2026

Results:

image image

@greptile-apps
Copy link
Copy Markdown

greptile-apps Bot commented Feb 3, 2026

Greptile Overview

Greptile Summary

Optimized Poseidon hash functions by eliminating unnecessary heap allocations. Changed hash() and hash_single() to use stack-allocated arrays instead of Vec, and refactored hash_many() to perform in-place state mutations instead of allocating a new Vec for each block. These changes significantly reduce memory allocations in hot paths, especially beneficial for Merkle tree operations that call hash_many frequently.

Confidence Score: 5/5

  • This PR is safe to merge with minimal risk
  • The changes are well-scoped optimizations that replace heap allocations with stack allocations and eliminate redundant copying. The semantics remain unchanged, as the trait signature for hades_permutation already accepts &mut [FE<Self::F>] which works with both arrays and vectors. Existing tests validate correctness, and the PR author confirms benchmarks were run.
  • No files require special attention

Important Files Changed

Filename Overview
crates/crypto/src/hash/poseidon/mod.rs Replaced heap-allocated Vec with stack arrays for state in hash/hash_single, and eliminated per-block allocations in hash_many through in-place mutation

Sequence Diagram

sequenceDiagram
    participant Client
    participant Poseidon
    participant State
    participant Hades

    Note over Client,Hades: hash() function flow
    Client->>Poseidon: hash(x, y)
    Poseidon->>State: Create [x, y, FE(2)] on stack
    Poseidon->>Hades: hades_permutation(&mut state)
    Hades->>State: Apply full rounds
    Hades->>State: Apply partial rounds
    Hades->>State: Apply full rounds
    Hades-->>Poseidon: Modified state
    Poseidon-->>Client: Return state[0]

    Note over Client,Hades: hash_many() function flow
    Client->>Poseidon: hash_many(inputs)
    Poseidon->>State: Create Vec of size m (STATE_SIZE)
    loop For each block of size r
        Poseidon->>State: Add block values in-place to state[..r]
        Poseidon->>Hades: hades_permutation(&mut state)
        Hades->>State: Apply full and partial rounds
    end
    Poseidon-->>Client: Return state[0]
Loading

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.

1 participant