Zeth - Zerocash on Ethereum  0.8
Reference implementation of the Zeth protocol by Clearmatics
mpc_linear_combination.cpp
Go to the documentation of this file.
1 // Copyright (c) 2015-2022 Clearmatics Technologies Ltd
2 //
3 // SPDX-License-Identifier: LGPL-3.0+
4 
6 #include "libzeth/core/utils.hpp"
9 #include "mpc_common.hpp"
10 
11 #include <boost/program_options.hpp>
12 #include <functional>
13 #include <vector>
14 
15 using namespace libzeth;
16 using pp = defaults::pp;
17 namespace po = boost::program_options;
18 
19 namespace
20 {
21 
22 // Usage:
23 // mpc linear-combination [<option>]
24 // <powersoftau file> <lagrange file> <linear_comb_file>
25 //
26 // Options:
27 // -h,--help This message
28 // --pot-degree powersoftau degree (assumed equal to lagrange file)
29 // --verify Skip computation. Load and verify input data.
30 class mpc_linear_combination : public mpc_subcommand
31 {
32  std::string powersoftau_file;
33  std::string lagrange_file;
34  size_t powersoftau_degree;
35  std::string out_file;
36  bool verify;
37 
38 public:
39  mpc_linear_combination()
41  "linear-combination", "Create linear combination for our circuit")
42  , powersoftau_file()
43  , lagrange_file()
44  , powersoftau_degree(0)
45  , out_file()
46  , verify(false)
47  {
48  }
49 
50 private:
51  void initialize_suboptions(
52  po::options_description &options,
53  po::options_description &all_options,
54  po::positional_options_description &pos) override
55  {
56  options.add_options()(
57  "pot-degree",
58  po::value<size_t>(),
59  "powersoftau degree (assumed equal to lagrange file)")(
60  "verify", "Skip computation. Load and verify input data");
61  all_options.add(options).add_options()(
62  "powersoftau_file", po::value<std::string>(), "powersoftau file")(
63  "lagrange_file", po::value<std::string>(), "lagrange file")(
64  "linear_comb_file",
65  po::value<std::string>(),
66  "linear combination output");
67  pos.add("powersoftau_file", 1)
68  .add("lagrange_file", 1)
69  .add("linear_comb_file", 1);
70  }
71 
72  void parse_suboptions(const po::variables_map &vm) override
73  {
74  if (0 == vm.count("powersoftau_file")) {
75  throw po::error("powersoftau_file not specified");
76  }
77  if (0 == vm.count("lagrange_file")) {
78  throw po::error("lagrange_file not specified");
79  }
80  if (0 == vm.count("linear_comb_file")) {
81  throw po::error("linear_comb_file not specified");
82  }
83 
84  powersoftau_file = vm["powersoftau_file"].as<std::string>();
85  lagrange_file = vm["lagrange_file"].as<std::string>();
86  out_file = vm["linear_comb_file"].as<std::string>();
87  powersoftau_degree =
88  vm.count("pot-degree") ? vm["pot-degree"].as<size_t>() : 0;
89  verify = (bool)vm.count("verify");
90  }
91 
92  void subcommand_usage(const char *argv0) override
93  {
94  std::cout << "Usage:\n " << argv0 << " " << subcommand_name
95  << " [<options>] <powersoftau file> <lagrange file> "
96  "<linear_comb_file>\n";
97  }
98 
99  int execute_subcommand(const global_options &options) override
100  {
101  if (options.verbose) {
102  std::cout << "powersoftau_file: " << powersoftau_file << "\n"
103  << "lagrange_file: " << lagrange_file << "\n"
104  << "powersoftau_degree: " << powersoftau_degree << "\n"
105  << "out_file: " << out_file << "\n"
106  << "verify: " << std::to_string(verify) << std::endl;
107  }
108 
109  // Load lagrange evaluations to determine n, then load powersoftau
110  // TODO: Load just degree from lagrange data, then load the two
111  // files in parallel.
112  libff::enter_block("Load Lagrange data");
113  libff::print_indent();
114  std::cout << lagrange_file << std::endl;
115  const srs_lagrange_evaluations<pp> lagrange =
116  read_from_file<srs_lagrange_evaluations<pp>>(lagrange_file);
117  libff::leave_block("Load Lagrange data");
118 
119  libff::enter_block("Load powers of tau");
120  libff::print_indent();
121  std::cout << powersoftau_file << std::endl;
122  const srs_powersoftau<pp> pot = [this, &lagrange]() {
123  std::ifstream in(
124  powersoftau_file, std::ios_base::binary | std::ios_base::in);
125  const size_t pot_degree =
126  powersoftau_degree ? powersoftau_degree : lagrange.degree;
127  return powersoftau_load<pp>(in, pot_degree);
128  }();
129  libff::leave_block("Load powers of tau");
130 
131  // Compute circuit
132  libff::enter_block("Generate QAP");
133  libsnark::protoboard<Field> pb;
134  options.protoboard_init(pb);
135  const libsnark::r1cs_constraint_system<Field> cs =
136  pb.get_constraint_system();
137  const libsnark::qap_instance<Field> qap =
138  libsnark::r1cs_to_qap_instance_map(cs, true);
139  libff::leave_block("Generate QAP");
140 
141  // Early-out if "--verify" was specified
142  if (verify) {
143  std::cout << "verify: skipping computation and write.)"
144  << std::endl;
145  return 0;
146  }
147 
148  // Compute final step of linear combination
149  if (qap.degree() != lagrange.degree) {
150  throw std::invalid_argument(
151  "Degree of qap " + std::to_string(qap.degree()) + " does not " +
152  "match degree of lagrange evaluations. Regenerate with "
153  "matching " +
154  "degree.");
155  }
156 
157  // Compute layer1 and write to a file
158  const srs_mpc_layer_L1<pp> lin_comb =
159  mpc_compute_linearcombination<pp>(pot, lagrange, qap);
160 
161  libff::enter_block("Writing linear combination file");
162  libff::print_indent();
163  std::cout << out_file << std::endl;
164  {
165  std::ofstream out(
166  out_file, std::ios_base::binary | std::ios_base::out);
167  lin_comb.write(out);
168  }
169  libff::leave_block("Writing linear combination file");
170 
171  return 0;
172  }
173 };
174 
175 } // namespace
176 
177 mpc_subcommand *mpc_linear_combination_cmd = new mpc_linear_combination();
mpc_common.hpp
mpc_utils.hpp
blake2s_comp.hpp
utils.hpp
libzeth::srs_mpc_layer_L1::write
void write(std::ostream &out) const
libzeth
Definition: binary_operation.hpp:15
global_options::verbose
bool verbose
Definition: mpc_subcommand.hpp:19
global_options
Definition: mpc_subcommand.hpp:15
global_options::protoboard_init
ProtoboardInitFn protoboard_init
Definition: mpc_subcommand.hpp:18
libzeth::srs_lagrange_evaluations
Definition: mpc_utils.hpp:32
libzeth::srs_mpc_layer_L1
Definition: mpc_utils.hpp:37
libzeth::srs_lagrange_evaluations::degree
const size_t degree
Definition: powersoftau_utils.hpp:51
mpc_subcommand
libtool::subcommand< global_options > mpc_subcommand
Definition: mpc_subcommand.hpp:22
zeth.core.signing.verify
bool verify(SigningVerificationKey vk, bytes m, int sigma)
Definition: signing.py:145
pp
defaults::pp pp
Definition: mpc_linear_combination.cpp:16
libzeth::srs_powersoftau
Definition: mpc_utils.hpp:31
pp
defaults::pp pp
Definition: mpc_create_keypair.cpp:14
powersoftau_utils.hpp
mpc_linear_combination_cmd
mpc_subcommand * mpc_linear_combination_cmd
Definition: mpc_linear_combination.cpp:177
libtool::subcommand
Class representing a tool subcommand.
Definition: subcommand.hpp:18