14
14
15
15
using json = nlohmann::json;
16
16
17
+ static size_t ProofBufferMinSize ()
18
+ {
19
+ return 726 ;
20
+ }
17
21
18
- int
19
- groth16_prover ( const void *zkey_buffer, unsigned long zkey_size,
20
- const void *wtns_buffer, unsigned long wtns_size,
21
- char *proof_buffer, unsigned long proof_size,
22
- char *public_buffer, unsigned long public_size,
23
- char *error_msg, unsigned long error_msg_maxsize )
22
+ static size_t PublicBufferMinSize ( size_t count)
23
+ {
24
+ return count * 81 + 3 ;
25
+ }
26
+
27
+ static void VerifyPrimes (mpz_srcptr zkey_prime, mpz_srcptr wtns_prime )
24
28
{
25
29
mpz_t altBbn128r;
26
30
27
31
mpz_init (altBbn128r);
28
32
mpz_set_str (altBbn128r, " 21888242871839275222246405745257275088548364400416034343698204186575808495617" , 10 );
29
33
34
+ if (mpz_cmp (zkey_prime, altBbn128r) != 0 ) {
35
+ throw std::invalid_argument ( " zkey curve not supported" );
36
+ }
37
+
38
+ if (mpz_cmp (wtns_prime, altBbn128r) != 0 ) {
39
+ throw std::invalid_argument ( " different wtns curve" );
40
+ }
41
+
42
+ mpz_clear (altBbn128r);
43
+ }
44
+
45
+ std::string BuildPublicString (AltBn128::FrElement *wtnsData, size_t nPublic)
46
+ {
47
+ json jsonPublic;
48
+ AltBn128::FrElement aux;
49
+ for (u_int32_t i=1 ; i<= nPublic; i++) {
50
+ AltBn128::Fr.toMontgomery (aux, wtnsData[i]);
51
+ jsonPublic.push_back (AltBn128::Fr.toString (aux));
52
+ }
53
+
54
+ return jsonPublic.dump ();
55
+ }
56
+
57
+ int
58
+ groth16_prover (const void *zkey_buffer, unsigned long zkey_size,
59
+ const void *wtns_buffer, unsigned long wtns_size,
60
+ char *proof_buffer, unsigned long *proof_size,
61
+ char *public_buffer, unsigned long *public_size,
62
+ char *error_msg, unsigned long error_msg_maxsize)
63
+ {
30
64
try {
31
65
BinFileUtils::BinFile zkey (zkey_buffer, zkey_size, " zkey" , 1 );
32
-
33
66
auto zkeyHeader = ZKeyUtils::loadHeader (&zkey);
34
67
35
- std::string proofStr;
36
- if (mpz_cmp (zkeyHeader->rPrime , altBbn128r) != 0 ) {
37
- throw std::invalid_argument ( " zkey curve not supported" );
38
- }
39
-
40
68
BinFileUtils::BinFile wtns (wtns_buffer, wtns_size, " wtns" , 2 );
41
69
auto wtnsHeader = WtnsUtils::loadHeader (&wtns);
42
70
43
- if (mpz_cmp (wtnsHeader->prime , altBbn128r) != 0 ) {
44
- throw std::invalid_argument ( " different wtns curve" );
71
+ size_t proofMinSize = ProofBufferMinSize ();
72
+ size_t publicMinSize = PublicBufferMinSize (zkeyHeader->nPublic );
73
+
74
+ if (*proof_size < proofMinSize || *public_size < publicMinSize) {
75
+
76
+ *proof_size = proofMinSize;
77
+ *public_size = publicMinSize;
78
+
79
+ return PPROVER_ERROR_SHORT_BUFFER;
45
80
}
46
81
82
+ VerifyPrimes (zkeyHeader->rPrime , wtnsHeader->prime );
83
+
47
84
auto prover = Groth16::makeProver<AltBn128::Engine>(
48
85
zkeyHeader->nVars ,
49
86
zkeyHeader->nPublic ,
@@ -65,30 +102,43 @@ groth16_prover(const void *zkey_buffer, unsigned long zkey_size,
65
102
auto proof = prover->prove (wtnsData);
66
103
67
104
std::string stringProof = proof->toJson ().dump ();
105
+ std::string stringPublic = BuildPublicString (wtnsData, zkeyHeader->nPublic );
68
106
69
- std::strncpy (proof_buffer, stringProof.data (), proof_size);
107
+ size_t stringProofSize = stringProof.length ();
108
+ size_t stringPublicSize = stringPublic.length ();
70
109
71
- json jsonPublic;
72
- AltBn128::FrElement aux;
73
- for (u_int32_t i=1 ; i<=zkeyHeader->nPublic ; i++) {
74
- AltBn128::Fr.toMontgomery (aux, wtnsData[i]);
75
- jsonPublic.push_back (AltBn128::Fr.toString (aux));
76
- }
110
+ if (*proof_size < stringProofSize || *public_size < stringPublicSize) {
77
111
78
- std::string stringPublic = jsonPublic.dump ();
112
+ *proof_size = stringProofSize;
113
+ *public_size = stringPublicSize;
79
114
80
- std::strncpy (public_buffer, stringPublic.data (), public_size);
115
+ return PPROVER_ERROR_SHORT_BUFFER;
116
+ }
117
+
118
+ std::strncpy (proof_buffer, stringProof.data (), *proof_size);
119
+ std::strncpy (public_buffer, stringPublic.data (), *public_size);
81
120
82
121
} catch (std::exception & e) {
83
- mpz_clear (altBbn128r);
84
122
85
123
if (error_msg) {
86
124
strncpy (error_msg, e.what (), error_msg_maxsize);
87
125
}
88
126
return PPROVER_ERROR;
89
- }
90
127
91
- mpz_clear (altBbn128r);
128
+ } catch (std::exception *e) {
129
+
130
+ if (error_msg) {
131
+ strncpy (error_msg, e->what (), error_msg_maxsize);
132
+ }
133
+ delete e;
134
+ return PPROVER_ERROR;
135
+
136
+ } catch (...) {
137
+ if (error_msg) {
138
+ strncpy (error_msg, " unknown error" , error_msg_maxsize);
139
+ }
140
+ return PPROVER_ERROR;
141
+ }
92
142
93
143
return PRPOVER_OK;
94
144
}
0 commit comments