Skip to content

Commit

Permalink
feat: ultra rollup flows (#10162)
Browse files Browse the repository at this point in the history
Adds new flows to bb main for UltraRollupFlavor. Modifies honk recursion
constraint to be able to extract IPA claims and call accumulate on them.

closes #1153
  • Loading branch information
lucasxia01 authored and AztecBot committed Dec 3, 2024
1 parent a5b4ec7 commit 0fe0a5d
Show file tree
Hide file tree
Showing 12 changed files with 67 additions and 31 deletions.
22 changes: 17 additions & 5 deletions cpp/src/barretenberg/bb/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1465,6 +1465,12 @@ int main(int argc, char* argv[])
} else if (command == "prove_ultra_honk_output_all") {
std::string output_path = get_option(args, "-o", "./proofs");
prove_honk_output_all<UltraFlavor>(bytecode_path, witness_path, output_path, recursive);
} else if (command == "prove_ultra_rollup_honk_output_all") {
std::string output_path = get_option(args, "-o", "./proofs/proof");
prove_honk_output_all<UltraRollupFlavor>(bytecode_path, witness_path, output_path, recursive);
} else if (command == "prove_ultra_keccak_honk_output_all") {
std::string output_path = get_option(args, "-o", "./proofs/proof");
prove_honk_output_all<UltraKeccakFlavor>(bytecode_path, witness_path, output_path, recursive);
} else if (command == "prove_mega_honk_output_all") {
std::string output_path = get_option(args, "-o", "./proofs");
prove_honk_output_all<MegaFlavor>(bytecode_path, witness_path, output_path, recursive);
Expand Down Expand Up @@ -1526,9 +1532,9 @@ int main(int argc, char* argv[])
} else if (command == "prove_ultra_keccak_honk") {
std::string output_path = get_option(args, "-o", "./proofs/proof");
prove_honk<UltraKeccakFlavor>(bytecode_path, witness_path, output_path, recursive);
} else if (command == "prove_ultra_keccak_honk_output_all") {
} else if (command == "prove_ultra_rollup_honk") {
std::string output_path = get_option(args, "-o", "./proofs/proof");
prove_honk_output_all<UltraKeccakFlavor>(bytecode_path, witness_path, output_path, recursive);
prove_honk<UltraRollupFlavor>(bytecode_path, witness_path, output_path, recursive);
} else if (command == "verify_ultra_honk") {
return verify_honk<UltraFlavor>(proof_path, vk_path) ? 0 : 1;
} else if (command == "verify_ultra_keccak_honk") {
Expand All @@ -1539,6 +1545,9 @@ int main(int argc, char* argv[])
} else if (command == "write_vk_ultra_keccak_honk") {
std::string output_path = get_option(args, "-o", "./target/vk");
write_vk_honk<UltraKeccakFlavor>(bytecode_path, output_path, recursive);
} else if (command == "write_vk_ultra_rollup_honk") {
std::string output_path = get_option(args, "-o", "./target/vk");
write_vk_honk<UltraRollupFlavor>(bytecode_path, output_path, recursive);
} else if (command == "prove_mega_honk") {
std::string output_path = get_option(args, "-o", "./proofs/proof");
prove_honk<MegaFlavor>(bytecode_path, witness_path, output_path, recursive);
Expand All @@ -1553,12 +1562,15 @@ int main(int argc, char* argv[])
} else if (command == "vk_as_fields_ultra_honk") {
std::string output_path = get_option(args, "-o", vk_path + "_fields.json");
vk_as_fields_honk<UltraFlavor>(vk_path, output_path);
} else if (command == "vk_as_fields_mega_honk") {
std::string output_path = get_option(args, "-o", vk_path + "_fields.json");
vk_as_fields_honk<MegaFlavor>(vk_path, output_path);
} else if (command == "vk_as_fields_ultra_keccak_honk") {
std::string output_path = get_option(args, "-o", vk_path + "_fields.json");
vk_as_fields_honk<UltraKeccakFlavor>(vk_path, output_path);
} else if (command == "vk_as_fields_ultra_rollup_honk") {
std::string output_path = get_option(args, "-o", vk_path + "_fields.json");
vk_as_fields_honk<UltraRollupFlavor>(vk_path, output_path);
} else if (command == "vk_as_fields_mega_honk") {
std::string output_path = get_option(args, "-o", vk_path + "_fields.json");
vk_as_fields_honk<MegaFlavor>(vk_path, output_path);
} else {
std::cerr << "Unknown command: " << command << "\n";
return 1;
Expand Down
10 changes: 4 additions & 6 deletions cpp/src/barretenberg/commitment_schemes/claim.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -60,12 +60,10 @@ template <typename Curve> class OpeningClaim {
opening_pair.challenge.binary_basis_limbs[1].element.normalize().witness_index,
opening_pair.challenge.binary_basis_limbs[2].element.normalize().witness_index,
opening_pair.challenge.binary_basis_limbs[3].element.normalize().witness_index,
// TODO(https://github.com/AztecProtocol/barretenberg/issues/1153): Uncomment this when we turn the
// eval into witnesses.
// opening_pair.evaluation.binary_basis_limbs[0].element.normalize().witness_index,
// opening_pair.evaluation.binary_basis_limbs[1].element.normalize().witness_index,
// opening_pair.evaluation.binary_basis_limbs[2].element.normalize().witness_index,
// opening_pair.evaluation.binary_basis_limbs[3].element.normalize().witness_index,
opening_pair.evaluation.binary_basis_limbs[0].element.normalize().witness_index,
opening_pair.evaluation.binary_basis_limbs[1].element.normalize().witness_index,
opening_pair.evaluation.binary_basis_limbs[2].element.normalize().witness_index,
opening_pair.evaluation.binary_basis_limbs[3].element.normalize().witness_index,
commitment.x.normalize().witness_index, // no idea if we need these normalize() calls...
commitment.y.normalize().witness_index };
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -113,6 +113,7 @@ std::vector<typename GeminiProver_<Curve>::Claim> GeminiProver_<Curve>::prove(
std::move(batched_to_be_shifted),
std::move(batched_concatenated));

// TODO(https://github.com/AztecProtocol/barretenberg/issues/1159): Decouple constants from primitives.
for (size_t l = 0; l < CONST_PROOF_SIZE_LOG_N - 1; l++) {
if (l < log_n - 1) {
transcript->send_to_verifier("Gemini:FOLD_" + std::to_string(l + 1),
Expand Down
1 change: 1 addition & 0 deletions cpp/src/barretenberg/commitment_schemes/ipa/ipa.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -200,6 +200,7 @@ template <typename Curve_> class IPA {

// Iterate for log(poly_degree) rounds to compute the round commitments.
auto log_poly_length = static_cast<size_t>(numeric::get_msb(poly_length));
// TODO(https://github.com/AztecProtocol/barretenberg/issues/1159): Decouple constant from IPA.
if (log_poly_length > CONST_ECCVM_LOG_N) {
throw_or_abort("IPA log_poly_length is too large");
}
Expand Down
1 change: 1 addition & 0 deletions cpp/src/barretenberg/commitment_schemes/ipa/ipa.test.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -159,6 +159,7 @@ TEST_F(IPATest, AIsZeroAfterOneRound)

// initialize an empty mock transcript
auto transcript = std::make_shared<MockTranscript>();
// TODO(https://github.com/AztecProtocol/barretenberg/issues/1159): Decouple constant from IPA.
const size_t num_challenges = CONST_ECCVM_LOG_N + 1;
std::vector<uint256_t> random_vector(num_challenges);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -469,6 +469,7 @@ template <typename Curve> class ShpleminiVerifier_ {

// Initialize batching challenge as ν²
Fr current_batching_challenge = shplonk_batching_challenge.sqr();
// TODO(https://github.com/AztecProtocol/barretenberg/issues/1159): Decouple constants from primitives.
for (size_t j = 0; j < CONST_PROOF_SIZE_LOG_N - 1; ++j) {
// Compute the scaling factor (ν²⁺ⁱ) / (z + r²⁽ⁱ⁺²⁾) for i = 0, … , d-2
Fr scaling_factor = current_batching_challenge * inverse_vanishing_evals[j + 2];
Expand Down
9 changes: 7 additions & 2 deletions cpp/src/barretenberg/commitment_schemes/shplonk/shplonk.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
#include "barretenberg/commitment_schemes/claim.hpp"
#include "barretenberg/commitment_schemes/commitment_key.hpp"
#include "barretenberg/commitment_schemes/verification_key.hpp"
#include "barretenberg/stdlib/primitives/curves/bn254.hpp"
#include "barretenberg/transcript/transcript.hpp"

/**
Expand Down Expand Up @@ -224,7 +225,9 @@ template <typename Curve> class ShplonkVerifier_ {
// [G] = [Q] - ∑ⱼ (1/zⱼ(r))[Bⱼ] + ( ∑ⱼ (1/zⱼ(r)) Tⱼ(r) )[1]
// = [Q] - ∑ⱼ (1/zⱼ(r))[Bⱼ] + G₀ [1]
// G₀ = ∑ⱼ ρʲ ⋅ vⱼ / (z − xⱼ )
auto G_commitment_constant = Fr(0);
Fr G_commitment_constant(0);

Fr evaluation(0);

// TODO(#673): The recursive and non-recursive (native) logic is completely separated via the following
// conditional. Much of the logic could be shared, but I've chosen to do it this way since soon the "else"
Expand Down Expand Up @@ -274,6 +277,8 @@ template <typename Curve> class ShplonkVerifier_ {
// [G] += G₀⋅[1] = [G] + (∑ⱼ νʲ ⋅ vⱼ / (z − xⱼ ))⋅[1]
G_commitment = GroupElement::batch_mul(commitments, scalars);

// Set evaluation to constant witness
evaluation.convert_constant_to_fixed_witness(z_challenge.get_context());
} else {
// [G] = [Q] - ∑ⱼ νʲ / (z − xⱼ )⋅[fⱼ] + G₀⋅[1]
// = [Q] - [∑ⱼ νʲ ⋅ ( fⱼ(X) − vⱼ) / (z − xⱼ )]
Expand Down Expand Up @@ -309,7 +314,7 @@ template <typename Curve> class ShplonkVerifier_ {
}

// Return opening pair (z, 0) and commitment [G]
return { { z_challenge, Fr(0) }, G_commitment };
return { { z_challenge, evaluation }, G_commitment };
};
/**
* @brief Computes \f$ \frac{1}{z - r}, \frac{1}{z+r}, \ldots, \frac{1}{z+r^{2^{d-1}}} \f$.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -421,6 +421,7 @@ template <typename Curve> class ZeroMorphProver_ {
transcript->send_to_verifier(label, q_k_commitment);
}
// Add buffer elements to remove log_N dependence in proof
// TODO(https://github.com/AztecProtocol/barretenberg/issues/1159): Decouple constants from primitives.
for (size_t idx = log_N; idx < CONST_PROOF_SIZE_LOG_N; ++idx) {
auto buffer_element = Commitment::one();
std::string label = "ZM:C_q_" + std::to_string(idx);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ using PairingPointAccumulatorIndices = std::array<uint32_t, PAIRING_POINT_ACCUMU
// of the nested aggregation object.
using PairingPointAccumulatorPubInputIndices = std::array<uint32_t, PAIRING_POINT_ACCUMULATOR_SIZE>;

static constexpr uint32_t IPA_CLAIM_SIZE = 6;
static constexpr uint32_t IPA_CLAIM_SIZE = 10;
using IPAClaimIndices = std::array<uint32_t, IPA_CLAIM_SIZE>;
using IPAClaimPubInputIndices = std::array<uint32_t, IPA_CLAIM_SIZE>;
} // namespace bb
Original file line number Diff line number Diff line change
Expand Up @@ -133,7 +133,7 @@ UltraRecursiveVerifier_<Flavor>::Output UltraRecursiveVerifier_<Flavor>::verify_
// Extract the IPA claim from the public inputs
// Parse out the nested IPA claim using key->ipa_claim_public_input_indices and runs the native IPA verifier.
if constexpr (HasIPAAccumulator<Flavor>) {
const auto recover_fq_from_public_inputs = [](std::array<FF, 4>& limbs) {
const auto recover_fq_from_public_inputs = [](std::array<FF, Curve::BaseField::NUM_LIMBS>& limbs) {
for (size_t k = 0; k < Curve::BaseField::NUM_LIMBS; k++) {
limbs[k].create_range_constraint(Curve::BaseField::NUM_LIMB_BITS, "limb_" + std::to_string(k));
}
Expand All @@ -142,18 +142,25 @@ UltraRecursiveVerifier_<Flavor>::Output UltraRecursiveVerifier_<Flavor>::verify_

if (verification_key->verification_key->contains_ipa_claim) {
OpeningClaim<grumpkin<Builder>> ipa_claim;
std::array<FF, 4> bigfield_limbs;
for (size_t k = 0; k < 4; k++) {
bigfield_limbs[k] =
std::array<FF, Curve::BaseField::NUM_LIMBS> challenge_bigfield_limbs;
for (size_t k = 0; k < Curve::BaseField::NUM_LIMBS; k++) {
challenge_bigfield_limbs[k] =
verification_key
->public_inputs[verification_key->verification_key->ipa_claim_public_input_indices[k]];
}
ipa_claim.opening_pair.challenge = recover_fq_from_public_inputs(bigfield_limbs);
ipa_claim.opening_pair.evaluation = 0;
std::array<FF, Curve::BaseField::NUM_LIMBS> evaluation_bigfield_limbs;
for (size_t k = 0; k < Curve::BaseField::NUM_LIMBS; k++) {
evaluation_bigfield_limbs[k] =
verification_key
->public_inputs[verification_key->verification_key
->ipa_claim_public_input_indices[Curve::BaseField::NUM_LIMBS + k]];
}
ipa_claim.opening_pair.challenge = recover_fq_from_public_inputs(challenge_bigfield_limbs);
ipa_claim.opening_pair.evaluation = recover_fq_from_public_inputs(evaluation_bigfield_limbs);
ipa_claim.commitment = {
verification_key->public_inputs[verification_key->verification_key->ipa_claim_public_input_indices[4]],
verification_key->public_inputs[verification_key->verification_key->ipa_claim_public_input_indices[5]],
false // WORKTODO: make this a witness?
verification_key->public_inputs[verification_key->verification_key->ipa_claim_public_input_indices[8]],
verification_key->public_inputs[verification_key->verification_key->ipa_claim_public_input_indices[9]],
false
};
output.ipa_opening_claim = std::move(ipa_claim);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -450,7 +450,7 @@ template <typename Builder, typename T> class bigfield {

void set_origin_tag(const bb::OriginTag& tag) const
{
for (size_t i = 0; i < 4; i++) {
for (size_t i = 0; i < NUM_LIMBS; i++) {
binary_basis_limbs[i].element.set_origin_tag(tag);
}
prime_basis_limb.set_origin_tag(tag);
Expand Down
23 changes: 16 additions & 7 deletions cpp/src/barretenberg/ultra_honk/ultra_verifier.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -34,18 +34,27 @@ template <typename Flavor> bool UltraVerifier_<Flavor>::verify_proof(const HonkP
// Parse out the nested IPA claim using key->ipa_claim_public_input_indices and runs the native IPA verifier.
if constexpr (HasIPAAccumulator<Flavor>) {
if (verification_key->verification_key->contains_ipa_claim) {

constexpr size_t NUM_LIMBS = 4;
OpeningClaim<curve::Grumpkin> ipa_claim;
std::array<FF, 4> bigfield_limbs;
for (size_t k = 0; k < 4; k++) {
bigfield_limbs[k] =

std::array<FF, NUM_LIMBS> challenge_bigfield_limbs;
std::array<FF, NUM_LIMBS> evaluation_bigfield_limbs;
for (size_t k = 0; k < NUM_LIMBS; k++) {
challenge_bigfield_limbs[k] =
verification_key
->public_inputs[verification_key->verification_key->ipa_claim_public_input_indices[k]];
}
ipa_claim.opening_pair.challenge = recover_fq_from_public_inputs(bigfield_limbs);
ipa_claim.opening_pair.evaluation = 0;
for (size_t k = 0; k < NUM_LIMBS; k++) {
evaluation_bigfield_limbs[k] =
verification_key->public_inputs[verification_key->verification_key
->ipa_claim_public_input_indices[NUM_LIMBS + k]];
}
ipa_claim.opening_pair.challenge = recover_fq_from_public_inputs(challenge_bigfield_limbs);
ipa_claim.opening_pair.evaluation = recover_fq_from_public_inputs(evaluation_bigfield_limbs);
ipa_claim.commitment = {
verification_key->public_inputs[verification_key->verification_key->ipa_claim_public_input_indices[4]],
verification_key->public_inputs[verification_key->verification_key->ipa_claim_public_input_indices[5]]
verification_key->public_inputs[verification_key->verification_key->ipa_claim_public_input_indices[8]],
verification_key->public_inputs[verification_key->verification_key->ipa_claim_public_input_indices[9]]
};

// verify the ipa_proof with this claim
Expand Down

0 comments on commit 0fe0a5d

Please sign in to comment.