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(avm-main): pil -> permutations #3650

Merged
merged 12 commits into from
Dec 14, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion barretenberg/.gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -5,4 +5,5 @@ node_modules
ts/dest
.tsbuildinfo
.idea
cmake-build-debug
cmake-build-debug
*_opt.pil
20 changes: 20 additions & 0 deletions barretenberg/cpp/pil/avm/toy_avm.pil
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
namespace toy(256);
pol commit q_tuple_set;

// Set 1
pol commit set_1_column_1;
pol commit set_1_column_2;
// Set 2
pol commit set_2_column_1;
pol commit set_2_column_2;

// This is a column based tuple lookup
#[two_column_perm] // the name of the inverse
q_tuple_set { set_1_column_1, set_1_column_2 } is { set_2_column_1, set_2_column_2 };

// Relation not used -> we currently require a single relation for codegen
pol commit x;
x' - x = 0;

// Also needs a fixed relation
pol fixed first = [1] + [0]*;
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@
#include "barretenberg/polynomials/barycentric.hpp"
#include "barretenberg/polynomials/univariate.hpp"

#include "barretenberg/relations/generic_permutation/generic_permutation_relation.hpp"

#include "barretenberg/flavor/flavor.hpp"
#include "barretenberg/flavor/flavor_macros.hpp"
#include "barretenberg/polynomials/evaluation_domain.hpp"
Expand Down Expand Up @@ -40,7 +42,7 @@ class AvmMiniFlavor {
// the unshifted and one for the shifted
static constexpr size_t NUM_ALL_ENTITIES = 30;

using Relations = std::tuple<AvmMini_vm::avm_mini<FF>, AvmMini_vm::mem_trace<FF>>;
using Relations = std::tuple<AvmMini_vm::mem_trace<FF>, AvmMini_vm::avm_mini<FF>>;

static constexpr size_t MAX_PARTIAL_RELATION_LENGTH = compute_max_partial_relation_length<Relations>();

Expand Down Expand Up @@ -144,8 +146,8 @@ class AvmMiniFlavor {
avmMini_mem_idx_c,
avmMini_last,
memTrace_m_rw_shift,
memTrace_m_val_shift,
memTrace_m_addr_shift)
memTrace_m_addr_shift,
memTrace_m_val_shift)

RefVector<DataType> get_wires()
{
Expand Down Expand Up @@ -177,8 +179,8 @@ class AvmMiniFlavor {
avmMini_mem_idx_c,
avmMini_last,
memTrace_m_rw_shift,
memTrace_m_val_shift,
memTrace_m_addr_shift };
memTrace_m_addr_shift,
memTrace_m_val_shift };
};
RefVector<DataType> get_unshifted()
{
Expand Down Expand Up @@ -210,10 +212,10 @@ class AvmMiniFlavor {
avmMini_mem_idx_c,
avmMini_last };
};
RefVector<DataType> get_to_be_shifted() { return { memTrace_m_rw, memTrace_m_val, memTrace_m_addr }; };
RefVector<DataType> get_to_be_shifted() { return { memTrace_m_rw, memTrace_m_addr, memTrace_m_val }; };
RefVector<DataType> get_shifted()
{
return { memTrace_m_rw_shift, memTrace_m_val_shift, memTrace_m_addr_shift };
return { memTrace_m_rw_shift, memTrace_m_addr_shift, memTrace_m_val_shift };
};
};

Expand Down Expand Up @@ -467,4 +469,6 @@ class AvmMiniFlavor {
};

} // namespace flavor

namespace sumcheck {}
} // namespace proof_system::honk
304 changes: 304 additions & 0 deletions barretenberg/cpp/src/barretenberg/flavor/generated/Toy_flavor.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,304 @@


#pragma once
#include "../relation_definitions_fwd.hpp"
#include "barretenberg/commitment_schemes/kzg/kzg.hpp"
#include "barretenberg/ecc/curves/bn254/g1.hpp"
#include "barretenberg/polynomials/barycentric.hpp"
#include "barretenberg/polynomials/univariate.hpp"

#include "barretenberg/relations/generic_permutation/generic_permutation_relation.hpp"

#include "barretenberg/flavor/flavor.hpp"
#include "barretenberg/flavor/flavor_macros.hpp"
#include "barretenberg/polynomials/evaluation_domain.hpp"
#include "barretenberg/polynomials/polynomial.hpp"
#include "barretenberg/relations/generated/Toy/toy_avm.hpp"
#include "barretenberg/relations/generated/Toy/two_column_perm.hpp"
#include "barretenberg/transcript/transcript.hpp"

namespace proof_system::honk {
namespace flavor {

class ToyFlavor {
public:
using Curve = curve::BN254;
using G1 = Curve::Group;
using PCS = pcs::kzg::KZG<Curve>;

using FF = G1::subgroup_field;
using Polynomial = barretenberg::Polynomial<FF>;
using PolynomialHandle = std::span<FF>;
using GroupElement = G1::element;
using Commitment = G1::affine_element;
using CommitmentHandle = G1::affine_element;
using CommitmentKey = pcs::CommitmentKey<Curve>;
using VerifierCommitmentKey = pcs::VerifierCommitmentKey<Curve>;

static constexpr size_t NUM_PRECOMPUTED_ENTITIES = 1;
static constexpr size_t NUM_WITNESS_ENTITIES = 7;
static constexpr size_t NUM_WIRES = NUM_WITNESS_ENTITIES + NUM_PRECOMPUTED_ENTITIES;
// We have two copies of the witness entities, so we subtract the number of fixed ones (they have no shift), one for
// the unshifted and one for the shifted
static constexpr size_t NUM_ALL_ENTITIES = 9;

using Relations = std::tuple<Toy_vm::toy_avm<FF>, sumcheck::two_column_perm_relation<FF>>;

static constexpr size_t MAX_PARTIAL_RELATION_LENGTH = compute_max_partial_relation_length<Relations>();

// BATCHED_RELATION_PARTIAL_LENGTH = algebraic degree of sumcheck relation *after* multiplying by the `pow_zeta`
// random polynomial e.g. For \sum(x) [A(x) * B(x) + C(x)] * PowZeta(X), relation length = 2 and random relation
// length = 3
static constexpr size_t BATCHED_RELATION_PARTIAL_LENGTH = MAX_PARTIAL_RELATION_LENGTH + 1;
static constexpr size_t NUM_RELATIONS = std::tuple_size<Relations>::value;

template <size_t NUM_INSTANCES>
using ProtogalaxyTupleOfTuplesOfUnivariates =
decltype(create_protogalaxy_tuple_of_tuples_of_univariates<Relations, NUM_INSTANCES>());
using SumcheckTupleOfTuplesOfUnivariates = decltype(create_sumcheck_tuple_of_tuples_of_univariates<Relations>());
using TupleOfArraysOfValues = decltype(create_tuple_of_arrays_of_values<Relations>());

static constexpr bool has_zero_row = true;

private:
template <typename DataType_> class PrecomputedEntities : public PrecomputedEntitiesBase {
public:
using DataType = DataType_;

DEFINE_FLAVOR_MEMBERS(DataType, toy_first)

RefVector<DataType> get_selectors() { return { toy_first }; };
RefVector<DataType> get_sigma_polynomials() { return {}; };
RefVector<DataType> get_id_polynomials() { return {}; };
RefVector<DataType> get_table_polynomials() { return {}; };
};

template <typename DataType> class WitnessEntities {
public:
DEFINE_FLAVOR_MEMBERS(DataType,
toy_q_tuple_set,
toy_set_1_column_1,
toy_set_1_column_2,
toy_set_2_column_1,
toy_set_2_column_2,
toy_x,
two_column_perm)

RefVector<DataType> get_wires()
{
return { toy_q_tuple_set, toy_set_1_column_1, toy_set_1_column_2, toy_set_2_column_1, toy_set_2_column_2,
toy_x, two_column_perm };
};
RefVector<DataType> get_sorted_polynomials() { return {}; };
};

template <typename DataType> class AllEntities {
public:
DEFINE_FLAVOR_MEMBERS(DataType,
toy_first,
toy_q_tuple_set,
toy_set_1_column_1,
toy_set_1_column_2,
toy_set_2_column_1,
toy_set_2_column_2,
toy_x,
two_column_perm,
toy_x_shift)

RefVector<DataType> get_wires()
{
return { toy_first, toy_q_tuple_set, toy_set_1_column_1, toy_set_1_column_2, toy_set_2_column_1,
toy_set_2_column_2, toy_x, two_column_perm, toy_x_shift };
};
RefVector<DataType> get_unshifted()
{
return { toy_first, toy_q_tuple_set, toy_set_1_column_1, toy_set_1_column_2, toy_set_2_column_1,
toy_set_2_column_2, toy_x, two_column_perm };
};
RefVector<DataType> get_to_be_shifted() { return { toy_x }; };
RefVector<DataType> get_shifted() { return { toy_x_shift }; };
};

public:
class ProvingKey : public ProvingKey_<PrecomputedEntities<Polynomial>, WitnessEntities<Polynomial>> {
public:
// Expose constructors on the base class
using Base = ProvingKey_<PrecomputedEntities<Polynomial>, WitnessEntities<Polynomial>>;
using Base::Base;

// The plookup wires that store plookup read data.
std::array<PolynomialHandle, 0> get_table_column_wires() { return {}; };
};

using VerificationKey = VerificationKey_<PrecomputedEntities<Commitment>>;

using ProverPolynomials = AllEntities<PolynomialHandle>;

using FoldedPolynomials = AllEntities<std::vector<FF>>;

class AllValues : public AllEntities<FF> {
public:
using Base = AllEntities<FF>;
using Base::Base;
};

class AllPolynomials : public AllEntities<Polynomial> {
public:
[[nodiscard]] size_t get_polynomial_size() const { return this->toy_q_tuple_set.size(); }
[[nodiscard]] AllValues get_row(const size_t row_idx) const
{
AllValues result;
for (auto [result_field, polynomial] : zip_view(result.get_all(), get_all())) {
result_field = polynomial[row_idx];
}
return result;
}
};

using RowPolynomials = AllEntities<FF>;

class PartiallyEvaluatedMultivariates : public AllEntities<Polynomial> {
public:
PartiallyEvaluatedMultivariates() = default;
PartiallyEvaluatedMultivariates(const size_t circuit_size)
{
// Storage is only needed after the first partial evaluation, hence polynomials of size (n / 2)
for (auto& poly : get_all()) {
poly = Polynomial(circuit_size / 2);
}
}
};

/**
* @brief A container for univariates used during Protogalaxy folding and sumcheck.
* @details During folding and sumcheck, the prover evaluates the relations on these univariates.
*/
template <size_t LENGTH> using ProverUnivariates = AllEntities<barretenberg::Univariate<FF, LENGTH>>;

/**
* @brief A container for univariates produced during the hot loop in sumcheck.
*/
using ExtendedEdges = ProverUnivariates<MAX_PARTIAL_RELATION_LENGTH>;

class CommitmentLabels : public AllEntities<std::string> {
private:
using Base = AllEntities<std::string>;

public:
CommitmentLabels()
: AllEntities<std::string>()
{
Base::toy_first = "TOY_FIRST";
Base::toy_q_tuple_set = "TOY_Q_TUPLE_SET";
Base::toy_set_1_column_1 = "TOY_SET_1_COLUMN_1";
Base::toy_set_1_column_2 = "TOY_SET_1_COLUMN_2";
Base::toy_set_2_column_1 = "TOY_SET_2_COLUMN_1";
Base::toy_set_2_column_2 = "TOY_SET_2_COLUMN_2";
Base::toy_x = "TOY_X";
Base::two_column_perm = "TWO_COLUMN_PERM";
};
};

class VerifierCommitments : public AllEntities<Commitment> {
private:
using Base = AllEntities<Commitment>;

public:
VerifierCommitments(const std::shared_ptr<VerificationKey>& verification_key)
{
toy_first = verification_key->toy_first;
}
};

class Transcript : public BaseTranscript {
public:
uint32_t circuit_size;

Commitment toy_q_tuple_set;
Commitment toy_set_1_column_1;
Commitment toy_set_1_column_2;
Commitment toy_set_2_column_1;
Commitment toy_set_2_column_2;
Commitment toy_x;
Commitment two_column_perm;

std::vector<barretenberg::Univariate<FF, BATCHED_RELATION_PARTIAL_LENGTH>> sumcheck_univariates;
std::array<FF, NUM_ALL_ENTITIES> sumcheck_evaluations;
std::vector<Commitment> zm_cq_comms;
Commitment zm_cq_comm;
Commitment zm_pi_comm;

Transcript() = default;

Transcript(const std::vector<uint8_t>& proof)
: BaseTranscript(proof)
{}

void deserialize_full_transcript()
{
size_t num_bytes_read = 0;
circuit_size = deserialize_from_buffer<uint32_t>(proof_data, num_bytes_read);
size_t log_n = numeric::get_msb(circuit_size);

toy_q_tuple_set = deserialize_from_buffer<Commitment>(Transcript::proof_data, num_bytes_read);
toy_set_1_column_1 = deserialize_from_buffer<Commitment>(Transcript::proof_data, num_bytes_read);
toy_set_1_column_2 = deserialize_from_buffer<Commitment>(Transcript::proof_data, num_bytes_read);
toy_set_2_column_1 = deserialize_from_buffer<Commitment>(Transcript::proof_data, num_bytes_read);
toy_set_2_column_2 = deserialize_from_buffer<Commitment>(Transcript::proof_data, num_bytes_read);
toy_x = deserialize_from_buffer<Commitment>(Transcript::proof_data, num_bytes_read);
two_column_perm = deserialize_from_buffer<Commitment>(Transcript::proof_data, num_bytes_read);

for (size_t i = 0; i < log_n; ++i) {
sumcheck_univariates.emplace_back(
deserialize_from_buffer<barretenberg::Univariate<FF, BATCHED_RELATION_PARTIAL_LENGTH>>(
Transcript::proof_data, num_bytes_read));
}
sumcheck_evaluations =
deserialize_from_buffer<std::array<FF, NUM_ALL_ENTITIES>>(Transcript::proof_data, num_bytes_read);
for (size_t i = 0; i < log_n; ++i) {
zm_cq_comms.push_back(deserialize_from_buffer<Commitment>(proof_data, num_bytes_read));
}
zm_cq_comm = deserialize_from_buffer<Commitment>(proof_data, num_bytes_read);
zm_pi_comm = deserialize_from_buffer<Commitment>(proof_data, num_bytes_read);
}

void serialize_full_transcript()
{
size_t old_proof_length = proof_data.size();
Transcript::proof_data.clear();
size_t log_n = numeric::get_msb(circuit_size);

serialize_to_buffer(circuit_size, Transcript::proof_data);

serialize_to_buffer<Commitment>(toy_q_tuple_set, Transcript::proof_data);
serialize_to_buffer<Commitment>(toy_set_1_column_1, Transcript::proof_data);
serialize_to_buffer<Commitment>(toy_set_1_column_2, Transcript::proof_data);
serialize_to_buffer<Commitment>(toy_set_2_column_1, Transcript::proof_data);
serialize_to_buffer<Commitment>(toy_set_2_column_2, Transcript::proof_data);
serialize_to_buffer<Commitment>(toy_x, Transcript::proof_data);
serialize_to_buffer<Commitment>(two_column_perm, Transcript::proof_data);

for (size_t i = 0; i < log_n; ++i) {
serialize_to_buffer(sumcheck_univariates[i], Transcript::proof_data);
}
serialize_to_buffer(sumcheck_evaluations, Transcript::proof_data);
for (size_t i = 0; i < log_n; ++i) {
serialize_to_buffer(zm_cq_comms[i], proof_data);
}
serialize_to_buffer(zm_cq_comm, proof_data);
serialize_to_buffer(zm_pi_comm, proof_data);

// sanity check to make sure we generate the same length of proof as before.
ASSERT(proof_data.size() == old_proof_length);
}
};
};

} // namespace flavor

namespace sumcheck {

DECLARE_SUMCHECK_RELATION_CLASS(two_column_perm, flavor::ToyFlavor);

}
} // namespace proof_system::honk
Loading
Loading