Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: translation evaluations: refactor + soundness fix #12051

Merged
merged 26 commits into from
Feb 27, 2025

Conversation

iakovenkos
Copy link
Contributor

@iakovenkos iakovenkos commented Feb 17, 2025

In the ECCVM, we have a special sub-protocol to prove the univariate evaluations of Op, Px, Py, z1, and z2. The corresponding logic used to be un-rolled in execute_pcs_rounds() and verify_proof(). I isolated this logic into separate methods for the following reasons:

  • It improves the readability of the main methods
  • This sub-protocol will be saturated by extra steps needed for ZK translation evaluations
  • There's a cleaner correspondence between the Prover and Verifier steps

The following Goblin soundness issue has been discovered:

  • The unvariate evaluation challenge evaluation_challenge_x sampled in ECCVM would be propagated from the ECCVMProver to the TranslatorProver and sent to the TranslatorVerifier meaning that a malicious GoblinProver was free to send any field element and choose accumulated_result.
  • Moreover, the extra batching challenge sampled after (by ECCVMProver/TranslatorVerifier) the translation evaluations proof seemed redundant and would have blocked the further changes. Namely, in the fix being implemented, we must enforce that the batching challenge used to compute the batched claim is the batching challenge used by the Translator.
  • Now TranslatorVerifier retrieves evaluation_challenge_x and batching_challenge_v as class members of ECCVMVerifier.

@iakovenkos iakovenkos self-assigned this Feb 17, 2025
@@ -157,50 +157,8 @@ void ECCVMProver::execute_pcs_rounds()
sumcheck_output.round_univariates,
sumcheck_output.round_univariate_evaluations);

// Get the challenge at which we evaluate all transcript polynomials as univariates
Copy link
Contributor Author

Choose a reason for hiding this comment

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

isolated into a separate method

@@ -0,0 +1,90 @@
#pragma once
Copy link
Contributor Author

Choose a reason for hiding this comment

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

It's a new class in a way similar to ZKSumcheckData. It is supposed to accept the eccvm transcript wires, extract, and concatenate the masking terms to prepare them for the SmallSubgroupIPA.

commitments.transcript_z1,
commitments.transcript_z2 };

const OpeningClaim translation_opening_claim = reduce_verify_translation_evaluations(transcript_commitments);
Copy link
Contributor Author

Choose a reason for hiding this comment

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

again, isolated the translation evaluations logic into a separarte method to improve readability and make it uniform with the prover class

@@ -209,9 +167,6 @@ void ECCVMProver::execute_pcs_rounds()

// Compute the opening proof for the batched opening claim with the univariate PCS
PCS::compute_opening_proof(key->commitment_key, batch_opening_claim, ipa_transcript);

// Produce another challenge passed as input to the translator verifier
translation_batching_challenge_v = transcript->template get_challenge<FF>("Translation:batching_challenge");
Copy link
Contributor Author

Choose a reason for hiding this comment

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

This was a very strange step, the challenge that has to be propagated is the batching_challenge_v produced in reduce_translation_evaluations

// Load the proof produced by the translator prover
transcript->load_proof(proof);

Flavor::VerifierCommitments commitments{ key };
Flavor::CommitmentLabels commitment_labels;

const auto circuit_size = transcript->template receive_from_prover<uint32_t>("circuit_size");
evaluation_input_x = transcript->template receive_from_prover<BF>("evaluation_input_x");
Copy link
Contributor Author

@iakovenkos iakovenkos Feb 20, 2025

Choose a reason for hiding this comment

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

this was not sound, the prover could've sent anything here, switched to the propagation of these challenges from the ECCVMVerifier to TranslatorVerifier.

@iakovenkos iakovenkos marked this pull request as ready for review February 20, 2025 14:37
@iakovenkos iakovenkos changed the title feat: translation evaluations with zk feat: translation evaluations with zk pt.1 Feb 20, 2025
@iakovenkos iakovenkos marked this pull request as draft February 25, 2025 14:19
@iakovenkos iakovenkos marked this pull request as ready for review February 25, 2025 15:02
@iakovenkos iakovenkos changed the title feat: translation evaluations with zk pt.1 feat: translation evaluations: refactor + soundness fix Feb 25, 2025
@@ -103,6 +103,36 @@ TEST_F(GoblinRecursiveVerifierTests, Basic)
}
}

// Check that the GoblinRecursiveVerifier circuit does not depend on the inputs.
Copy link
Contributor Author

Choose a reason for hiding this comment

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

Added this test to catch any discrepancies caused by interactions between different components of goblin

Copy link
Contributor

@ledwards2225 ledwards2225 left a comment

Choose a reason for hiding this comment

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

Looks great, just a couple of minor comments about naming and some comment typo fixes. Nice work!

@@ -24,4 +24,7 @@ static constexpr uint32_t MASKING_OFFSET = 4;
// For ZK Flavors: the number of the commitments required by Libra and SmallSubgroupIPA.
static constexpr uint32_t NUM_LIBRA_COMMITMENTS = 3;
static constexpr uint32_t NUM_LIBRA_EVALUATIONS = 4;
// There are 5 distinguished wires in ECCVM that have to be opened as univariates to establish the connection between
// ECCVM and Translator
static constexpr uint32_t NUM_TRANSLATION_EVALUATIONS = 5;
Copy link
Contributor

Choose a reason for hiding this comment

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

Seems like the eccvm flavor might be a better place for this constant

Copy link
Contributor Author

Choose a reason for hiding this comment

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

It was also implicitly used in TranslationEvaluations struct that is propagated to Translator, I just modified it to use this constant explicitly. It is also used by the SmallSubgroupIPA in #12244, so I'd keep it here. But probably we'll need to revise these constants at some point.

@ledwards2225 ledwards2225 removed the request for review from maramihali February 25, 2025 21:21
@iakovenkos iakovenkos merged commit 5359310 into master Feb 27, 2025
9 checks passed
@iakovenkos iakovenkos deleted the si/fix-translation-evaluations branch February 27, 2025 10:03
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.

2 participants