Skip to content

Commit

Permalink
added kzg_batched for 2 vectors of polynomials #113
Browse files Browse the repository at this point in the history
  • Loading branch information
tshchelovek authored and martun committed Aug 10, 2023
1 parent a41ad1b commit 5bad073
Show file tree
Hide file tree
Showing 2 changed files with 340 additions and 15 deletions.
147 changes: 139 additions & 8 deletions include/nil/crypto3/zk/commitments/polynomial/kzg.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,9 @@ namespace nil {
namespace crypto3 {
namespace zk {
namespace commitments {
template<typename CurveType>
struct kzg_commitment;

template<typename CurveType>
struct kzg_commitment {

Expand All @@ -66,8 +69,13 @@ namespace nil {
using proof_type = commitment_type;

struct kzg_params_type {
std::size_t n; //max polynomial degree
scalar_value_type alpha; //secret key
std::size_t n; //max polynomial degree
kzg_params_type(std::size_t _n, scalar_value_type _alpha) : n(_n), alpha(_alpha) {}
kzg_params_type(std::size_t _n) {
alpha = scalar_value_type::random_element();
n = _n;
}
};

struct srs_type {
Expand All @@ -93,7 +101,7 @@ namespace nil {

static commitment_type commit(const srs_type &srs,
const polynomial<scalar_value_type> &f) {
BOOST_ASSERT(f.size() <= srs.commitment_key.size());
// assert(f.size() <= srs.commitment_key.size());
return algebra::multiexp<multiexp_method>(srs.commitment_key.begin(),
srs.commitment_key.begin() + f.size(), f.begin(), f.end(), 1);
}
Expand All @@ -105,22 +113,22 @@ namespace nil {
}

static proof_type proof_eval(srs_type srs,
const polynomial<scalar_value_type> &f,
scalar_value_type i,
const polynomial<scalar_value_type> &f) {
scalar_value_type eval) {

const polynomial<scalar_value_type> denominator_polynom = {-i, 1};
const polynomial<scalar_value_type> q =
(f - polynomial<scalar_value_type>{f.evaluate(i)}) / denominator_polynom;
(f - polynomial<scalar_value_type>{eval}) / denominator_polynom;

proof_type p = commit(srs, q);
return p;
return commit(srs, q);
}

static bool verify_eval(srs_type srs,
proof_type p,
commitment_type C_f,
scalar_value_type i,
scalar_value_type eval,
proof_type p) {
scalar_value_type eval) {

auto A_1 = algebra::precompute_g1<curve_type>(p);
auto A_2 = algebra::precompute_g2<curve_type>(srs.verification_key -
Expand All @@ -135,6 +143,129 @@ namespace nil {
return gt_4 == gt_value_type::one();
}
};

template<typename CurveType>
struct kzg_batched_commitment : public kzg_commitment<CurveType> {

typedef CurveType curve_type;
typedef algebra::pairing::pairing_policy<curve_type> pairing_policy;
typedef typename curve_type::gt_type::value_type gt_value_type;

using multiexp_method = typename algebra::policies::multiexp_method_BDLO12;
using scalar_value_type = typename curve_type::scalar_field_type::value_type;
using commitment_key_type = std::vector<typename curve_type::template g1_type<>::value_type>;
using verification_key_type = typename curve_type::template g2_type<>::value_type;
using commitment_type = typename curve_type::template g1_type<>::value_type;

using kzg = kzg_commitment<CurveType>;
using kzg_params_type = typename kzg::kzg_params_type;
using srs_type = typename kzg::srs_type;

struct evals_type {
std::vector<scalar_value_type> evals_at_z0;
std::vector<scalar_value_type> evals_at_z1;
evals_type(const std::vector<scalar_value_type> &e1, const std::vector<scalar_value_type> &e2)
: evals_at_z0(e1), evals_at_z1(e2) {}
};

struct batched_proof_type {
commitment_type commit0;
commitment_type commit1;
batched_proof_type(commitment_type c0, commitment_type c1) : commit0(c0), commit1(c1) {}
};

static polynomial<scalar_value_type> accumulate(const std::vector<polynomial<scalar_value_type>> &polys,
const scalar_value_type &factor) {
std::size_t num = polys.size();
if (num == 1) return polys[0];

polynomial<scalar_value_type> result = polys[num - 1];
for (int i = num - 2; i >= 0; --i) {
result = result * factor + polys[i];
}
return result;
}

static evals_type evaluate_polynomials(const std::vector<polynomial<scalar_value_type>> &polys0,
const std::vector<polynomial<scalar_value_type>> &polys1,
scalar_value_type z0, scalar_value_type z1) {
std::vector<scalar_value_type> evals_at_z0;
for (const auto &poly : polys0) {
evals_at_z0.emplace_back(poly.evaluate(z0));
}

std::vector<scalar_value_type> evals_at_z1;
for (const auto &poly : polys1) {
evals_at_z1.emplace_back(poly.evaluate(z1));
}

return evals_type(evals_at_z0, evals_at_z1);
}

static std::vector<commitment_type> commit(const srs_type &srs,
const std::vector<polynomial<scalar_value_type>> &polys) {
std::vector<commitment_type> commitments;
for (const auto &poly : polys) {
commitments.emplace_back(kzg::commit(srs, poly));
}
return commitments;
}

static batched_proof_type proof_eval(const srs_type &srs,
const std::vector<polynomial<scalar_value_type>> &polys0,
const std::vector<polynomial<scalar_value_type>> &polys1,
const evals_type &evals,
scalar_value_type z0, scalar_value_type z1,
scalar_value_type gamma0, scalar_value_type gamma1) {

auto accum0 = accumulate(polys0, gamma0);
auto accum_eval0 = polynomial<scalar_value_type>{evals.evals_at_z0}.evaluate(gamma0);
typename kzg::proof_type proof0 = kzg::proof_eval(srs, accum0, z0, accum_eval0);

auto accum1 = accumulate(polys1, gamma1);
auto accum_eval1 = polynomial<scalar_value_type>{evals.evals_at_z1}.evaluate(gamma1);
typename kzg::proof_type proof1 = kzg::proof_eval(srs, accum1, z1, accum_eval1);

return batched_proof_type(proof0, proof1);
}

static bool verify_eval(srs_type srs,
const batched_proof_type &proof,
const evals_type &evals,
const std::vector<commitment_type> &commits0,
const std::vector<commitment_type> &commits1,
scalar_value_type z0, scalar_value_type z1,
scalar_value_type gamma0, scalar_value_type gamma1,
scalar_value_type r) {

auto eval0_accum = evals.evals_at_z0.back();
auto comm0_accum = commits0.back();
for (int i = commits0.size() - 2; i >= 0; --i) {
comm0_accum = (gamma0 * comm0_accum) + commits0[i];
eval0_accum = (eval0_accum * gamma0) + evals.evals_at_z0[i];
}

auto eval1_accum = evals.evals_at_z1.back();
auto comm1_accum = commits1.back();
for (int i = commits1.size() - 2; i >= 0; --i) {
comm1_accum = (gamma1 * comm1_accum) + commits1[i];
eval1_accum = (eval1_accum * gamma1) + evals.evals_at_z1[i];
}

auto F = (comm0_accum - eval0_accum * curve_type::template g1_type<>::value_type::one()) +
r * (comm1_accum - eval1_accum * curve_type::template g1_type<>::value_type::one());

auto A_1 = algebra::precompute_g1<curve_type>(F + z0 * proof.commit0 + z1 * r * proof.commit1);
auto A_2 = algebra::precompute_g2<curve_type>(curve_type::template g2_type<>::value_type::one());
auto B_1 = algebra::precompute_g1<curve_type>(-proof.commit0 - r * proof.commit1);
auto B_2 = algebra::precompute_g2<curve_type>(srs.verification_key);

gt_value_type gt3 = algebra::double_miller_loop<curve_type>(A_1, A_2, B_1, B_2);
gt_value_type gt_4 = algebra::final_exponentiation<curve_type>(gt3);

return gt_4 == gt_value_type::one();
}
};
}; // namespace commitments
} // namespace zk
} // namespace crypto3
Expand Down
Loading

0 comments on commit 5bad073

Please sign in to comment.