Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
o1js: o1-labs/o1js#1338
This reimplements conversion of Rust field elements to Zarith bigints (
Bigint.to_bignum_bigint
). The conversion is used for theHashable
implementation of field elements, which previously was one of the main bottlenecks during witness generation, becauseplonk_constraint_system.ml
uses a hashtable with field element keys.The old conversion tested each individual bit of the Rust field. The new version tests 32 bits at once, and introduces a new bindings function
test_uint32
for this purpose.Empirically, this PR makes brings the witness generation time in a JS benchmark (Keccak) down by about 60%, from 1.7 to 0.7 seconds. The cost of
hash
calls, which used to be >50%, becomes negligible.Note: IMO, this isn't the cleanest way to achieve the goal. It keeps the dependency on Zarith -- a separate, arbitrary-length bigint implementation, which is slow at least in the JS version -- just for support of a few methods like
Hashable.hash
. Ideally, we would implement hashing in Rust and JS and get rid of Zarith. However, that's a more impactful change and would have required more research. This here seems to be the minimal change that removes the bottleneck.TODO: So far, only the JS backend implements
test_uint32
. Rust and Rust/wasm versions have to be added.