Skip to content

Simplify missing cell handling in recovery#629

Merged
jtraglia merged 7 commits intoethereum:mainfrom
jtraglia:fr-comparisions-optimization
Feb 26, 2026
Merged

Simplify missing cell handling in recovery#629
jtraglia merged 7 commits intoethereum:mainfrom
jtraglia:fr-comparisions-optimization

Conversation

@jtraglia
Copy link
Member

@jtraglia jtraglia commented Feb 24, 2026

Originally, this PR was an optimization in field element comparisons which resulted in a 3% speed-up in compute_cells_and_kzg_proofs but the team was concerned with the changes. So we decided to revert the optimization changes and keep the simplification we noticed.

Copy link
Contributor

@b-wagn b-wagn left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM!

src/common/fr.c Outdated
blst_uint64_from_fr(a, p);
return a[0] == 1 && a[1] == 0 && a[2] == 0 && a[3] == 0;
bool fr_is_one(const fr_t *fr) {
return memcmp(fr, &FR_ONE, sizeof(fr_t)) == 0;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This switch to memcmp is not truly straightforward because the old approach (using blst_uint64_from_fr()) was doing a modular reduction on the input field element. Whereas now we don't, and this could be a problem if this function ever receives an unreduced field element.

I don't think this is a problem, because we should not be handling unreduced field elements, but it's a new assumption that should be taken into account every time we parse or introduce field elements in any way.

src/common/fr.c Outdated
bool fr_is_null(const fr_t *p) {
return fr_equal(p, &FR_NULL);
bool fr_is_null(const fr_t *fr) {
return memcmp(fr, &FR_NULL, sizeof(fr_t)) == 0;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hmm, FR_NULL is only used during recovery and nowhere else. Perhaps we can just kill FR_NULL completely, and initialize recovered_cells_fr with FR_ZERO. After all, the missing cells will be set to zero by multiplication with vanishing_poly_eval. This is what's done in the spec right now (see extended_evaluation_rbo).

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh you're right. I like this suggestion. Let me do this.

src/common/fr.h Outdated
bool fr_is_one(const fr_t *p);
bool fr_is_null(const fr_t *p);
bool fr_is_zero(const fr_t *fr);
bool fr_is_one(const fr_t *fr);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can these be removed?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oops good catch, removed.

Copy link
Contributor

@asn-d6 asn-d6 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The recovery part seems good to me. I still don't like fr_equal() using memcmp.

Can't we just keep the recovery improvement?

@jtraglia jtraglia changed the title Use memcmp for field element comparisons Simplify missing cell handling in recovery Feb 26, 2026
@jtraglia jtraglia merged commit 673d93c into ethereum:main Feb 26, 2026
50 of 52 checks passed
@jtraglia jtraglia deleted the fr-comparisions-optimization branch February 26, 2026 14:12
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.

4 participants