/src/secp256k1/src/secp256k1.c
Line | Count | Source (jump to first uncovered line) |
1 | | /*********************************************************************** |
2 | | * Copyright (c) 2013-2015 Pieter Wuille * |
3 | | * Distributed under the MIT software license, see the accompanying * |
4 | | * file COPYING or https://www.opensource.org/licenses/mit-license.php.* |
5 | | ***********************************************************************/ |
6 | | |
7 | | /* This is a C project. It should not be compiled with a C++ compiler, |
8 | | * and we error out if we detect one. |
9 | | * |
10 | | * We still want to be able to test the project with a C++ compiler |
11 | | * because it is still good to know if this will lead to real trouble, so |
12 | | * there is a possibility to override the check. But be warned that |
13 | | * compiling with a C++ compiler is not supported. */ |
14 | | #if defined(__cplusplus) && !defined(SECP256K1_CPLUSPLUS_TEST_OVERRIDE) |
15 | | #error Trying to compile a C project with a C++ compiler. |
16 | | #endif |
17 | | |
18 | | #define SECP256K1_BUILD |
19 | | |
20 | | #include "../include/secp256k1.h" |
21 | | #include "../include/secp256k1_preallocated.h" |
22 | | |
23 | | #include "assumptions.h" |
24 | | #include "checkmem.h" |
25 | | #include "util.h" |
26 | | |
27 | | #include "field_impl.h" |
28 | | #include "scalar_impl.h" |
29 | | #include "group_impl.h" |
30 | | #include "ecmult_impl.h" |
31 | | #include "ecmult_const_impl.h" |
32 | | #include "ecmult_gen_impl.h" |
33 | | #include "ecdsa_impl.h" |
34 | | #include "eckey_impl.h" |
35 | | #include "hash_impl.h" |
36 | | #include "int128_impl.h" |
37 | | #include "scratch_impl.h" |
38 | | #include "selftest.h" |
39 | | #include "hsort_impl.h" |
40 | | |
41 | | #ifdef SECP256K1_NO_BUILD |
42 | | # error "secp256k1.h processed without SECP256K1_BUILD defined while building secp256k1.c" |
43 | | #endif |
44 | | |
45 | 50.5M | #define ARG_CHECK(cond) do { \ |
46 | 50.5M | if (EXPECT(!(cond), 0)) { \ |
47 | 0 | secp256k1_callback_call(&ctx->illegal_callback, #cond); \ |
48 | 0 | return 0; \ |
49 | 0 | } \ |
50 | 50.5M | } while(0) |
51 | | |
52 | 60.9k | #define ARG_CHECK_VOID(cond) do { \ |
53 | 60.9k | if (EXPECT(!(cond), 0)) { \ |
54 | 0 | secp256k1_callback_call(&ctx->illegal_callback, #cond); \ |
55 | 0 | return; \ |
56 | 0 | } \ |
57 | 60.9k | } while(0) |
58 | | |
59 | | /* Note that whenever you change the context struct, you must also change the |
60 | | * context_eq function. */ |
61 | | struct secp256k1_context_struct { |
62 | | secp256k1_ecmult_gen_context ecmult_gen_ctx; |
63 | | secp256k1_callback illegal_callback; |
64 | | secp256k1_callback error_callback; |
65 | | int declassify; |
66 | | }; |
67 | | |
68 | | static const secp256k1_context secp256k1_context_static_ = { |
69 | | { 0 }, |
70 | | { secp256k1_default_illegal_callback_fn, 0 }, |
71 | | { secp256k1_default_error_callback_fn, 0 }, |
72 | | 0 |
73 | | }; |
74 | | const secp256k1_context *secp256k1_context_static = &secp256k1_context_static_; |
75 | | const secp256k1_context *secp256k1_context_no_precomp = &secp256k1_context_static_; |
76 | | |
77 | | /* Helper function that determines if a context is proper, i.e., is not the static context or a copy thereof. |
78 | | * |
79 | | * This is intended for "context" functions such as secp256k1_context_clone. Functions that need specific |
80 | | * features of a context should still check for these features directly. For example, a function that needs |
81 | | * ecmult_gen should directly check for the existence of the ecmult_gen context. */ |
82 | 103k | static int secp256k1_context_is_proper(const secp256k1_context* ctx) { |
83 | 103k | return secp256k1_ecmult_gen_context_is_built(&ctx->ecmult_gen_ctx); |
84 | 103k | } |
85 | | |
86 | 18.8k | void secp256k1_selftest(void) { |
87 | 18.8k | if (!secp256k1_selftest_passes()) { |
88 | 0 | secp256k1_callback_call(&default_error_callback, "self test failed"); |
89 | 0 | } |
90 | 18.8k | } |
91 | | |
92 | 37.7k | size_t secp256k1_context_preallocated_size(unsigned int flags) { |
93 | 37.7k | size_t ret = sizeof(secp256k1_context); |
94 | | /* A return value of 0 is reserved as an indicator for errors when we call this function internally. */ |
95 | 37.7k | VERIFY_CHECK(ret != 0); |
96 | | |
97 | 37.7k | if (EXPECT((flags & SECP256K1_FLAGS_TYPE_MASK) != SECP256K1_FLAGS_TYPE_CONTEXT, 0)) { |
98 | 0 | secp256k1_callback_call(&default_illegal_callback, |
99 | 0 | "Invalid flags"); |
100 | 0 | return 0; |
101 | 0 | } |
102 | | |
103 | 37.7k | if (EXPECT(!SECP256K1_CHECKMEM_RUNNING() && (flags & SECP256K1_FLAGS_BIT_CONTEXT_DECLASSIFY), 0)) { |
104 | 0 | secp256k1_callback_call(&default_illegal_callback, |
105 | 0 | "Declassify flag requires running with memory checking"); |
106 | 0 | return 0; |
107 | 0 | } |
108 | | |
109 | 37.7k | return ret; |
110 | 37.7k | } |
111 | | |
112 | 11.4k | size_t secp256k1_context_preallocated_clone_size(const secp256k1_context* ctx) { |
113 | 11.4k | VERIFY_CHECK(ctx != NULL); |
114 | 11.4k | ARG_CHECK(secp256k1_context_is_proper(ctx)); |
115 | 11.4k | return sizeof(secp256k1_context); |
116 | 11.4k | } |
117 | | |
118 | 18.8k | secp256k1_context* secp256k1_context_preallocated_create(void* prealloc, unsigned int flags) { |
119 | 18.8k | size_t prealloc_size; |
120 | 18.8k | secp256k1_context* ret; |
121 | | |
122 | 18.8k | secp256k1_selftest(); |
123 | | |
124 | 18.8k | prealloc_size = secp256k1_context_preallocated_size(flags); |
125 | 18.8k | if (prealloc_size == 0) { |
126 | 0 | return NULL; |
127 | 0 | } |
128 | 18.8k | VERIFY_CHECK(prealloc != NULL); |
129 | 18.8k | ret = (secp256k1_context*)prealloc; |
130 | 18.8k | ret->illegal_callback = default_illegal_callback; |
131 | 18.8k | ret->error_callback = default_error_callback; |
132 | | |
133 | | /* Flags have been checked by secp256k1_context_preallocated_size. */ |
134 | 18.8k | VERIFY_CHECK((flags & SECP256K1_FLAGS_TYPE_MASK) == SECP256K1_FLAGS_TYPE_CONTEXT); |
135 | 18.8k | secp256k1_ecmult_gen_context_build(&ret->ecmult_gen_ctx); |
136 | 18.8k | ret->declassify = !!(flags & SECP256K1_FLAGS_BIT_CONTEXT_DECLASSIFY); |
137 | | |
138 | 18.8k | return ret; |
139 | 18.8k | } |
140 | | |
141 | 18.8k | secp256k1_context* secp256k1_context_create(unsigned int flags) { |
142 | 18.8k | size_t const prealloc_size = secp256k1_context_preallocated_size(flags); |
143 | 18.8k | secp256k1_context* ctx = (secp256k1_context*)checked_malloc(&default_error_callback, prealloc_size); |
144 | 18.8k | if (EXPECT(secp256k1_context_preallocated_create(ctx, flags) == NULL, 0)) { |
145 | 0 | free(ctx); |
146 | 0 | return NULL; |
147 | 0 | } |
148 | | |
149 | 18.8k | return ctx; |
150 | 18.8k | } |
151 | | |
152 | 11.4k | secp256k1_context* secp256k1_context_preallocated_clone(const secp256k1_context* ctx, void* prealloc) { |
153 | 11.4k | secp256k1_context* ret; |
154 | 11.4k | VERIFY_CHECK(ctx != NULL); |
155 | 11.4k | ARG_CHECK(prealloc != NULL); |
156 | 11.4k | ARG_CHECK(secp256k1_context_is_proper(ctx)); |
157 | | |
158 | 11.4k | ret = (secp256k1_context*)prealloc; |
159 | 11.4k | *ret = *ctx; |
160 | 11.4k | return ret; |
161 | 11.4k | } |
162 | | |
163 | 11.4k | secp256k1_context* secp256k1_context_clone(const secp256k1_context* ctx) { |
164 | 11.4k | secp256k1_context* ret; |
165 | 11.4k | size_t prealloc_size; |
166 | | |
167 | 11.4k | VERIFY_CHECK(ctx != NULL); |
168 | 11.4k | ARG_CHECK(secp256k1_context_is_proper(ctx)); |
169 | | |
170 | 11.4k | prealloc_size = secp256k1_context_preallocated_clone_size(ctx); |
171 | 11.4k | ret = (secp256k1_context*)checked_malloc(&ctx->error_callback, prealloc_size); |
172 | 11.4k | ret = secp256k1_context_preallocated_clone(ctx, ret); |
173 | 11.4k | return ret; |
174 | 11.4k | } |
175 | | |
176 | 30.4k | void secp256k1_context_preallocated_destroy(secp256k1_context* ctx) { |
177 | 30.4k | ARG_CHECK_VOID(ctx == NULL || secp256k1_context_is_proper(ctx)); |
178 | | |
179 | | /* Defined as noop */ |
180 | 30.4k | if (ctx == NULL) { |
181 | 0 | return; |
182 | 0 | } |
183 | | |
184 | 30.4k | secp256k1_ecmult_gen_context_clear(&ctx->ecmult_gen_ctx); |
185 | 30.4k | } |
186 | | |
187 | 30.4k | void secp256k1_context_destroy(secp256k1_context* ctx) { |
188 | 30.4k | ARG_CHECK_VOID(ctx == NULL || secp256k1_context_is_proper(ctx)); |
189 | | |
190 | | /* Defined as noop */ |
191 | 30.4k | if (ctx == NULL) { |
192 | 0 | return; |
193 | 0 | } |
194 | | |
195 | 30.4k | secp256k1_context_preallocated_destroy(ctx); |
196 | 30.4k | free(ctx); |
197 | 30.4k | } |
198 | | |
199 | 0 | void secp256k1_context_set_illegal_callback(secp256k1_context* ctx, void (*fun)(const char* message, void* data), const void* data) { |
200 | | /* We compare pointers instead of checking secp256k1_context_is_proper() here |
201 | | because setting callbacks is allowed on *copies* of the static context: |
202 | | it's harmless and makes testing easier. */ |
203 | 0 | ARG_CHECK_VOID(ctx != secp256k1_context_static); |
204 | 0 | if (fun == NULL) { |
205 | 0 | fun = secp256k1_default_illegal_callback_fn; |
206 | 0 | } |
207 | 0 | ctx->illegal_callback.fn = fun; |
208 | 0 | ctx->illegal_callback.data = data; |
209 | 0 | } |
210 | | |
211 | 0 | void secp256k1_context_set_error_callback(secp256k1_context* ctx, void (*fun)(const char* message, void* data), const void* data) { |
212 | | /* We compare pointers instead of checking secp256k1_context_is_proper() here |
213 | | because setting callbacks is allowed on *copies* of the static context: |
214 | | it's harmless and makes testing easier. */ |
215 | 0 | ARG_CHECK_VOID(ctx != secp256k1_context_static); |
216 | 0 | if (fun == NULL) { |
217 | 0 | fun = secp256k1_default_error_callback_fn; |
218 | 0 | } |
219 | 0 | ctx->error_callback.fn = fun; |
220 | 0 | ctx->error_callback.data = data; |
221 | 0 | } |
222 | | |
223 | 0 | secp256k1_scratch_space* secp256k1_scratch_space_create(const secp256k1_context* ctx, size_t max_size) { |
224 | 0 | VERIFY_CHECK(ctx != NULL); |
225 | 0 | return secp256k1_scratch_create(&ctx->error_callback, max_size); |
226 | 0 | } |
227 | | |
228 | 0 | void secp256k1_scratch_space_destroy(const secp256k1_context *ctx, secp256k1_scratch_space* scratch) { |
229 | 0 | VERIFY_CHECK(ctx != NULL); |
230 | 0 | secp256k1_scratch_destroy(&ctx->error_callback, scratch); |
231 | 0 | } |
232 | | |
233 | | /* Mark memory as no-longer-secret for the purpose of analysing constant-time behaviour |
234 | | * of the software. |
235 | | */ |
236 | 204k | static SECP256K1_INLINE void secp256k1_declassify(const secp256k1_context* ctx, const void *p, size_t len) { |
237 | 204k | if (EXPECT(ctx->declassify, 0)) SECP256K1_CHECKMEM_DEFINE(p, len); |
238 | 204k | } |
239 | | |
240 | 8.53M | static int secp256k1_pubkey_load(const secp256k1_context* ctx, secp256k1_ge* ge, const secp256k1_pubkey* pubkey) { |
241 | 8.53M | secp256k1_ge_storage s; |
242 | | |
243 | | /* We require that the secp256k1_ge_storage type is exactly 64 bytes. |
244 | | * This is formally not guaranteed by the C standard, but should hold on any |
245 | | * sane compiler in the real world. */ |
246 | 8.53M | STATIC_ASSERT(sizeof(secp256k1_ge_storage) == 64); |
247 | 8.53M | memcpy(&s, &pubkey->data[0], 64); |
248 | 8.53M | secp256k1_ge_from_storage(ge, &s); |
249 | 8.53M | ARG_CHECK(!secp256k1_fe_is_zero(&ge->x)); |
250 | 8.53M | return 1; |
251 | 8.53M | } |
252 | | |
253 | 9.75M | static void secp256k1_pubkey_save(secp256k1_pubkey* pubkey, secp256k1_ge* ge) { |
254 | 9.75M | secp256k1_ge_storage s; |
255 | | |
256 | 9.75M | STATIC_ASSERT(sizeof(secp256k1_ge_storage) == 64); |
257 | 9.75M | VERIFY_CHECK(!secp256k1_ge_is_infinity(ge)); |
258 | 9.75M | secp256k1_ge_to_storage(&s, ge); |
259 | 9.75M | memcpy(&pubkey->data[0], &s, 64); |
260 | 9.75M | } |
261 | | |
262 | 2.66M | int secp256k1_ec_pubkey_parse(const secp256k1_context* ctx, secp256k1_pubkey* pubkey, const unsigned char *input, size_t inputlen) { |
263 | 2.66M | secp256k1_ge Q; |
264 | | |
265 | 2.66M | VERIFY_CHECK(ctx != NULL); |
266 | 2.66M | ARG_CHECK(pubkey != NULL); |
267 | 2.66M | memset(pubkey, 0, sizeof(*pubkey)); |
268 | 2.66M | ARG_CHECK(input != NULL); |
269 | 2.66M | if (!secp256k1_eckey_pubkey_parse(&Q, input, inputlen)) { |
270 | 34.7k | return 0; |
271 | 34.7k | } |
272 | 2.63M | if (!secp256k1_ge_is_in_correct_subgroup(&Q)) { |
273 | 0 | return 0; |
274 | 0 | } |
275 | 2.63M | secp256k1_pubkey_save(pubkey, &Q); |
276 | 2.63M | secp256k1_ge_clear(&Q); |
277 | 2.63M | return 1; |
278 | 2.63M | } |
279 | | |
280 | 3.17M | int secp256k1_ec_pubkey_serialize(const secp256k1_context* ctx, unsigned char *output, size_t *outputlen, const secp256k1_pubkey* pubkey, unsigned int flags) { |
281 | 3.17M | secp256k1_ge Q; |
282 | 3.17M | size_t len; |
283 | 3.17M | int ret = 0; |
284 | | |
285 | 3.17M | VERIFY_CHECK(ctx != NULL); |
286 | 3.17M | ARG_CHECK(outputlen != NULL); |
287 | 3.17M | ARG_CHECK(*outputlen >= ((flags & SECP256K1_FLAGS_BIT_COMPRESSION) ? 33u : 65u)); |
288 | 3.17M | len = *outputlen; |
289 | 3.17M | *outputlen = 0; |
290 | 3.17M | ARG_CHECK(output != NULL); |
291 | 3.17M | memset(output, 0, len); |
292 | 3.17M | ARG_CHECK(pubkey != NULL); |
293 | 3.17M | ARG_CHECK((flags & SECP256K1_FLAGS_TYPE_MASK) == SECP256K1_FLAGS_TYPE_COMPRESSION); |
294 | 3.17M | if (secp256k1_pubkey_load(ctx, &Q, pubkey)) { |
295 | 3.17M | ret = secp256k1_eckey_pubkey_serialize(&Q, output, &len, flags & SECP256K1_FLAGS_BIT_COMPRESSION); |
296 | 3.17M | if (ret) { |
297 | 3.17M | *outputlen = len; |
298 | 3.17M | } |
299 | 3.17M | } |
300 | 3.17M | return ret; |
301 | 3.17M | } |
302 | | |
303 | 9.37k | int secp256k1_ec_pubkey_cmp(const secp256k1_context* ctx, const secp256k1_pubkey* pubkey0, const secp256k1_pubkey* pubkey1) { |
304 | 9.37k | unsigned char out[2][33]; |
305 | 9.37k | const secp256k1_pubkey* pk[2]; |
306 | 9.37k | int i; |
307 | | |
308 | 9.37k | VERIFY_CHECK(ctx != NULL); |
309 | 9.37k | pk[0] = pubkey0; pk[1] = pubkey1; |
310 | 28.1k | for (i = 0; i < 2; i++) { |
311 | 18.7k | size_t out_size = sizeof(out[i]); |
312 | | /* If the public key is NULL or invalid, ec_pubkey_serialize will call |
313 | | * the illegal_callback and return 0. In that case we will serialize the |
314 | | * key as all zeros which is less than any valid public key. This |
315 | | * results in consistent comparisons even if NULL or invalid pubkeys are |
316 | | * involved and prevents edge cases such as sorting algorithms that use |
317 | | * this function and do not terminate as a result. */ |
318 | 18.7k | if (!secp256k1_ec_pubkey_serialize(ctx, out[i], &out_size, pk[i], SECP256K1_EC_COMPRESSED)) { |
319 | | /* Note that ec_pubkey_serialize should already set the output to |
320 | | * zero in that case, but it's not guaranteed by the API, we can't |
321 | | * test it and writing a VERIFY_CHECK is more complex than |
322 | | * explicitly memsetting (again). */ |
323 | 0 | memset(out[i], 0, sizeof(out[i])); |
324 | 0 | } |
325 | 18.7k | } |
326 | 9.37k | return secp256k1_memcmp_var(out[0], out[1], sizeof(out[0])); |
327 | 9.37k | } |
328 | | |
329 | 0 | static int secp256k1_ec_pubkey_sort_cmp(const void* pk1, const void* pk2, void *ctx) { |
330 | 0 | return secp256k1_ec_pubkey_cmp((secp256k1_context *)ctx, |
331 | 0 | *(secp256k1_pubkey **)pk1, |
332 | 0 | *(secp256k1_pubkey **)pk2); |
333 | 0 | } |
334 | | |
335 | 0 | int secp256k1_ec_pubkey_sort(const secp256k1_context* ctx, const secp256k1_pubkey **pubkeys, size_t n_pubkeys) { |
336 | 0 | VERIFY_CHECK(ctx != NULL); |
337 | 0 | ARG_CHECK(pubkeys != NULL); |
338 | | |
339 | | /* Suppress wrong warning (fixed in MSVC 19.33) */ |
340 | | #if defined(_MSC_VER) && (_MSC_VER < 1933) |
341 | | #pragma warning(push) |
342 | | #pragma warning(disable: 4090) |
343 | | #endif |
344 | | |
345 | | /* Casting away const is fine because neither secp256k1_hsort nor |
346 | | * secp256k1_ec_pubkey_sort_cmp modify the data pointed to by the cmp_data |
347 | | * argument. */ |
348 | 0 | secp256k1_hsort(pubkeys, n_pubkeys, sizeof(*pubkeys), secp256k1_ec_pubkey_sort_cmp, (void *)ctx); |
349 | |
|
350 | | #if defined(_MSC_VER) && (_MSC_VER < 1933) |
351 | | #pragma warning(pop) |
352 | | #endif |
353 | |
|
354 | 0 | return 1; |
355 | 0 | } |
356 | | |
357 | 386k | static void secp256k1_ecdsa_signature_load(const secp256k1_context* ctx, secp256k1_scalar* r, secp256k1_scalar* s, const secp256k1_ecdsa_signature* sig) { |
358 | 386k | (void)ctx; |
359 | 386k | if (sizeof(secp256k1_scalar) == 32) { |
360 | | /* When the secp256k1_scalar type is exactly 32 byte, use its |
361 | | * representation inside secp256k1_ecdsa_signature, as conversion is very fast. |
362 | | * Note that secp256k1_ecdsa_signature_save must use the same representation. */ |
363 | 386k | memcpy(r, &sig->data[0], 32); |
364 | 386k | memcpy(s, &sig->data[32], 32); |
365 | 386k | } else { |
366 | 0 | secp256k1_scalar_set_b32(r, &sig->data[0], NULL); |
367 | 0 | secp256k1_scalar_set_b32(s, &sig->data[32], NULL); |
368 | 0 | } |
369 | 386k | } |
370 | | |
371 | 491k | static void secp256k1_ecdsa_signature_save(secp256k1_ecdsa_signature* sig, const secp256k1_scalar* r, const secp256k1_scalar* s) { |
372 | 491k | if (sizeof(secp256k1_scalar) == 32) { |
373 | 491k | memcpy(&sig->data[0], r, 32); |
374 | 491k | memcpy(&sig->data[32], s, 32); |
375 | 491k | } else { |
376 | 0 | secp256k1_scalar_get_b32(&sig->data[0], r); |
377 | 0 | secp256k1_scalar_get_b32(&sig->data[32], s); |
378 | 0 | } |
379 | 491k | } |
380 | | |
381 | 3.22k | int secp256k1_ecdsa_signature_parse_der(const secp256k1_context* ctx, secp256k1_ecdsa_signature* sig, const unsigned char *input, size_t inputlen) { |
382 | 3.22k | secp256k1_scalar r, s; |
383 | | |
384 | 3.22k | VERIFY_CHECK(ctx != NULL); |
385 | 3.22k | ARG_CHECK(sig != NULL); |
386 | 3.22k | ARG_CHECK(input != NULL); |
387 | | |
388 | 3.22k | if (secp256k1_ecdsa_sig_parse(&r, &s, input, inputlen)) { |
389 | 3.22k | secp256k1_ecdsa_signature_save(sig, &r, &s); |
390 | 3.22k | return 1; |
391 | 3.22k | } else { |
392 | 0 | memset(sig, 0, sizeof(*sig)); |
393 | 0 | return 0; |
394 | 0 | } |
395 | 3.22k | } |
396 | | |
397 | 337k | int secp256k1_ecdsa_signature_parse_compact(const secp256k1_context* ctx, secp256k1_ecdsa_signature* sig, const unsigned char *input64) { |
398 | 337k | secp256k1_scalar r, s; |
399 | 337k | int ret = 1; |
400 | 337k | int overflow = 0; |
401 | | |
402 | 337k | VERIFY_CHECK(ctx != NULL); |
403 | 337k | ARG_CHECK(sig != NULL); |
404 | 337k | ARG_CHECK(input64 != NULL); |
405 | | |
406 | 337k | secp256k1_scalar_set_b32(&r, &input64[0], &overflow); |
407 | 337k | ret &= !overflow; |
408 | 337k | secp256k1_scalar_set_b32(&s, &input64[32], &overflow); |
409 | 337k | ret &= !overflow; |
410 | 337k | if (ret) { |
411 | 336k | secp256k1_ecdsa_signature_save(sig, &r, &s); |
412 | 336k | } else { |
413 | 789 | memset(sig, 0, sizeof(*sig)); |
414 | 789 | } |
415 | 337k | return ret; |
416 | 337k | } |
417 | | |
418 | 36.3k | int secp256k1_ecdsa_signature_serialize_der(const secp256k1_context* ctx, unsigned char *output, size_t *outputlen, const secp256k1_ecdsa_signature* sig) { |
419 | 36.3k | secp256k1_scalar r, s; |
420 | | |
421 | 36.3k | VERIFY_CHECK(ctx != NULL); |
422 | 36.3k | ARG_CHECK(output != NULL); |
423 | 36.3k | ARG_CHECK(outputlen != NULL); |
424 | 36.3k | ARG_CHECK(sig != NULL); |
425 | | |
426 | 36.3k | secp256k1_ecdsa_signature_load(ctx, &r, &s, sig); |
427 | 36.3k | return secp256k1_ecdsa_sig_serialize(output, outputlen, &r, &s); |
428 | 36.3k | } |
429 | | |
430 | 76.4k | int secp256k1_ecdsa_signature_serialize_compact(const secp256k1_context* ctx, unsigned char *output64, const secp256k1_ecdsa_signature* sig) { |
431 | 76.4k | secp256k1_scalar r, s; |
432 | | |
433 | 76.4k | VERIFY_CHECK(ctx != NULL); |
434 | 76.4k | ARG_CHECK(output64 != NULL); |
435 | 76.4k | ARG_CHECK(sig != NULL); |
436 | | |
437 | 76.4k | secp256k1_ecdsa_signature_load(ctx, &r, &s, sig); |
438 | 76.4k | secp256k1_scalar_get_b32(&output64[0], &r); |
439 | 76.4k | secp256k1_scalar_get_b32(&output64[32], &s); |
440 | 76.4k | return 1; |
441 | 76.4k | } |
442 | | |
443 | 162k | int secp256k1_ecdsa_signature_normalize(const secp256k1_context* ctx, secp256k1_ecdsa_signature *sigout, const secp256k1_ecdsa_signature *sigin) { |
444 | 162k | secp256k1_scalar r, s; |
445 | 162k | int ret = 0; |
446 | | |
447 | 162k | VERIFY_CHECK(ctx != NULL); |
448 | 162k | ARG_CHECK(sigin != NULL); |
449 | | |
450 | 162k | secp256k1_ecdsa_signature_load(ctx, &r, &s, sigin); |
451 | 162k | ret = secp256k1_scalar_is_high(&s); |
452 | 162k | if (sigout != NULL) { |
453 | 78.1k | if (ret) { |
454 | 1.28k | secp256k1_scalar_negate(&s, &s); |
455 | 1.28k | } |
456 | 78.1k | secp256k1_ecdsa_signature_save(sigout, &r, &s); |
457 | 78.1k | } |
458 | | |
459 | 162k | return ret; |
460 | 162k | } |
461 | | |
462 | 111k | int secp256k1_ecdsa_verify(const secp256k1_context* ctx, const secp256k1_ecdsa_signature *sig, const unsigned char *msghash32, const secp256k1_pubkey *pubkey) { |
463 | 111k | secp256k1_ge q; |
464 | 111k | secp256k1_scalar r, s; |
465 | 111k | secp256k1_scalar m; |
466 | 111k | VERIFY_CHECK(ctx != NULL); |
467 | 111k | ARG_CHECK(msghash32 != NULL); |
468 | 111k | ARG_CHECK(sig != NULL); |
469 | 111k | ARG_CHECK(pubkey != NULL); |
470 | | |
471 | 111k | secp256k1_scalar_set_b32(&m, msghash32, NULL); |
472 | 111k | secp256k1_ecdsa_signature_load(ctx, &r, &s, sig); |
473 | 111k | return (!secp256k1_scalar_is_high(&s) && |
474 | 111k | secp256k1_pubkey_load(ctx, &q, pubkey) && |
475 | 111k | secp256k1_ecdsa_sig_verify(&r, &s, &q, &m)); |
476 | 111k | } |
477 | | |
478 | 199k | static SECP256K1_INLINE void buffer_append(unsigned char *buf, unsigned int *offset, const void *data, unsigned int len) { |
479 | 199k | memcpy(buf + *offset, data, len); |
480 | 199k | *offset += len; |
481 | 199k | } |
482 | | |
483 | 81.1k | static int nonce_function_rfc6979(unsigned char *nonce32, const unsigned char *msg32, const unsigned char *key32, const unsigned char *algo16, void *data, unsigned int counter) { |
484 | 81.1k | unsigned char keydata[112]; |
485 | 81.1k | unsigned int offset = 0; |
486 | 81.1k | secp256k1_rfc6979_hmac_sha256 rng; |
487 | 81.1k | unsigned int i; |
488 | 81.1k | secp256k1_scalar msg; |
489 | 81.1k | unsigned char msgmod32[32]; |
490 | 81.1k | secp256k1_scalar_set_b32(&msg, msg32, NULL); |
491 | 81.1k | secp256k1_scalar_get_b32(msgmod32, &msg); |
492 | | /* We feed a byte array to the PRNG as input, consisting of: |
493 | | * - the private key (32 bytes) and reduced message (32 bytes), see RFC 6979 3.2d. |
494 | | * - optionally 32 extra bytes of data, see RFC 6979 3.6 Additional Data. |
495 | | * - optionally 16 extra bytes with the algorithm name. |
496 | | * Because the arguments have distinct fixed lengths it is not possible for |
497 | | * different argument mixtures to emulate each other and result in the same |
498 | | * nonces. |
499 | | */ |
500 | 81.1k | buffer_append(keydata, &offset, key32, 32); |
501 | 81.1k | buffer_append(keydata, &offset, msgmod32, 32); |
502 | 81.1k | if (data != NULL) { |
503 | 37.4k | buffer_append(keydata, &offset, data, 32); |
504 | 37.4k | } |
505 | 81.1k | if (algo16 != NULL) { |
506 | 0 | buffer_append(keydata, &offset, algo16, 16); |
507 | 0 | } |
508 | 81.1k | secp256k1_rfc6979_hmac_sha256_initialize(&rng, keydata, offset); |
509 | 81.1k | memset(keydata, 0, sizeof(keydata)); |
510 | 162k | for (i = 0; i <= counter; i++) { |
511 | 81.1k | secp256k1_rfc6979_hmac_sha256_generate(&rng, nonce32, 32); |
512 | 81.1k | } |
513 | 81.1k | secp256k1_rfc6979_hmac_sha256_finalize(&rng); |
514 | 81.1k | return 1; |
515 | 81.1k | } |
516 | | |
517 | | const secp256k1_nonce_function secp256k1_nonce_function_rfc6979 = nonce_function_rfc6979; |
518 | | const secp256k1_nonce_function secp256k1_nonce_function_default = nonce_function_rfc6979; |
519 | | |
520 | 82.5k | static int secp256k1_ecdsa_sign_inner(const secp256k1_context* ctx, secp256k1_scalar* r, secp256k1_scalar* s, int* recid, const unsigned char *msg32, const unsigned char *seckey, secp256k1_nonce_function noncefp, const void* noncedata) { |
521 | 82.5k | secp256k1_scalar sec, non, msg; |
522 | 82.5k | int ret = 0; |
523 | 82.5k | int is_sec_valid; |
524 | 82.5k | unsigned char nonce32[32]; |
525 | 82.5k | unsigned int count = 0; |
526 | | /* Default initialization here is important so we won't pass uninit values to the cmov in the end */ |
527 | 82.5k | *r = secp256k1_scalar_zero; |
528 | 82.5k | *s = secp256k1_scalar_zero; |
529 | 82.5k | if (recid) { |
530 | 9.37k | *recid = 0; |
531 | 9.37k | } |
532 | 82.5k | if (noncefp == NULL) { |
533 | 0 | noncefp = secp256k1_nonce_function_default; |
534 | 0 | } |
535 | | |
536 | | /* Fail if the secret key is invalid. */ |
537 | 82.5k | is_sec_valid = secp256k1_scalar_set_b32_seckey(&sec, seckey); |
538 | 82.5k | secp256k1_scalar_cmov(&sec, &secp256k1_scalar_one, !is_sec_valid); |
539 | 82.5k | secp256k1_scalar_set_b32(&msg, msg32, NULL); |
540 | 82.5k | while (1) { |
541 | 82.5k | int is_nonce_valid; |
542 | 82.5k | ret = !!noncefp(nonce32, msg32, seckey, NULL, (void*)noncedata, count); |
543 | 82.5k | if (!ret) { |
544 | 6 | break; |
545 | 6 | } |
546 | 82.5k | is_nonce_valid = secp256k1_scalar_set_b32_seckey(&non, nonce32); |
547 | | /* The nonce is still secret here, but it being invalid is less likely than 1:2^255. */ |
548 | 82.5k | secp256k1_declassify(ctx, &is_nonce_valid, sizeof(is_nonce_valid)); |
549 | 82.5k | if (is_nonce_valid) { |
550 | 82.5k | ret = secp256k1_ecdsa_sig_sign(&ctx->ecmult_gen_ctx, r, s, &sec, &msg, &non, recid); |
551 | | /* The final signature is no longer a secret, nor is the fact that we were successful or not. */ |
552 | 82.5k | secp256k1_declassify(ctx, &ret, sizeof(ret)); |
553 | 82.5k | if (ret) { |
554 | 82.5k | break; |
555 | 82.5k | } |
556 | 82.5k | } |
557 | 6 | count++; |
558 | 6 | } |
559 | | /* We don't want to declassify is_sec_valid and therefore the range of |
560 | | * seckey. As a result is_sec_valid is included in ret only after ret was |
561 | | * used as a branching variable. */ |
562 | 82.5k | ret &= is_sec_valid; |
563 | 82.5k | memset(nonce32, 0, 32); |
564 | 82.5k | secp256k1_scalar_clear(&msg); |
565 | 82.5k | secp256k1_scalar_clear(&non); |
566 | 82.5k | secp256k1_scalar_clear(&sec); |
567 | 82.5k | secp256k1_scalar_cmov(r, &secp256k1_scalar_zero, !ret); |
568 | 82.5k | secp256k1_scalar_cmov(s, &secp256k1_scalar_zero, !ret); |
569 | 82.5k | if (recid) { |
570 | 9.37k | const int zero = 0; |
571 | 9.37k | secp256k1_int_cmov(recid, &zero, !ret); |
572 | 9.37k | } |
573 | 82.5k | return ret; |
574 | 82.5k | } |
575 | | |
576 | 73.2k | int secp256k1_ecdsa_sign(const secp256k1_context* ctx, secp256k1_ecdsa_signature *signature, const unsigned char *msghash32, const unsigned char *seckey, secp256k1_nonce_function noncefp, const void* noncedata) { |
577 | 73.2k | secp256k1_scalar r, s; |
578 | 73.2k | int ret; |
579 | 73.2k | VERIFY_CHECK(ctx != NULL); |
580 | 73.2k | ARG_CHECK(secp256k1_ecmult_gen_context_is_built(&ctx->ecmult_gen_ctx)); |
581 | 73.2k | ARG_CHECK(msghash32 != NULL); |
582 | 73.2k | ARG_CHECK(signature != NULL); |
583 | 73.2k | ARG_CHECK(seckey != NULL); |
584 | | |
585 | 73.2k | ret = secp256k1_ecdsa_sign_inner(ctx, &r, &s, NULL, msghash32, seckey, noncefp, noncedata); |
586 | 73.2k | secp256k1_ecdsa_signature_save(signature, &r, &s); |
587 | 73.2k | return ret; |
588 | 73.2k | } |
589 | | |
590 | 423k | int secp256k1_ec_seckey_verify(const secp256k1_context* ctx, const unsigned char *seckey) { |
591 | 423k | secp256k1_scalar sec; |
592 | 423k | int ret; |
593 | 423k | VERIFY_CHECK(ctx != NULL); |
594 | 423k | ARG_CHECK(seckey != NULL); |
595 | | |
596 | 423k | ret = secp256k1_scalar_set_b32_seckey(&sec, seckey); |
597 | 423k | secp256k1_scalar_clear(&sec); |
598 | 423k | return ret; |
599 | 423k | } |
600 | | |
601 | 898k | static int secp256k1_ec_pubkey_create_helper(const secp256k1_ecmult_gen_context *ecmult_gen_ctx, secp256k1_scalar *seckey_scalar, secp256k1_ge *p, const unsigned char *seckey) { |
602 | 898k | secp256k1_gej pj; |
603 | 898k | int ret; |
604 | | |
605 | 898k | ret = secp256k1_scalar_set_b32_seckey(seckey_scalar, seckey); |
606 | 898k | secp256k1_scalar_cmov(seckey_scalar, &secp256k1_scalar_one, !ret); |
607 | | |
608 | 898k | secp256k1_ecmult_gen(ecmult_gen_ctx, &pj, seckey_scalar); |
609 | 898k | secp256k1_ge_set_gej(p, &pj); |
610 | 898k | return ret; |
611 | 898k | } |
612 | | |
613 | 879k | int secp256k1_ec_pubkey_create(const secp256k1_context* ctx, secp256k1_pubkey *pubkey, const unsigned char *seckey) { |
614 | 879k | secp256k1_ge p; |
615 | 879k | secp256k1_scalar seckey_scalar; |
616 | 879k | int ret = 0; |
617 | 879k | VERIFY_CHECK(ctx != NULL); |
618 | 879k | ARG_CHECK(pubkey != NULL); |
619 | 879k | memset(pubkey, 0, sizeof(*pubkey)); |
620 | 879k | ARG_CHECK(secp256k1_ecmult_gen_context_is_built(&ctx->ecmult_gen_ctx)); |
621 | 879k | ARG_CHECK(seckey != NULL); |
622 | | |
623 | 879k | ret = secp256k1_ec_pubkey_create_helper(&ctx->ecmult_gen_ctx, &seckey_scalar, &p, seckey); |
624 | 879k | secp256k1_pubkey_save(pubkey, &p); |
625 | 879k | secp256k1_memczero(pubkey, sizeof(*pubkey), !ret); |
626 | | |
627 | 879k | secp256k1_scalar_clear(&seckey_scalar); |
628 | 879k | return ret; |
629 | 879k | } |
630 | | |
631 | 0 | int secp256k1_ec_seckey_negate(const secp256k1_context* ctx, unsigned char *seckey) { |
632 | 0 | secp256k1_scalar sec; |
633 | 0 | int ret = 0; |
634 | 0 | VERIFY_CHECK(ctx != NULL); |
635 | 0 | ARG_CHECK(seckey != NULL); |
636 | | |
637 | 0 | ret = secp256k1_scalar_set_b32_seckey(&sec, seckey); |
638 | 0 | secp256k1_scalar_cmov(&sec, &secp256k1_scalar_zero, !ret); |
639 | 0 | secp256k1_scalar_negate(&sec, &sec); |
640 | 0 | secp256k1_scalar_get_b32(seckey, &sec); |
641 | |
|
642 | 0 | secp256k1_scalar_clear(&sec); |
643 | 0 | return ret; |
644 | 0 | } |
645 | | |
646 | 0 | int secp256k1_ec_privkey_negate(const secp256k1_context* ctx, unsigned char *seckey) { |
647 | 0 | return secp256k1_ec_seckey_negate(ctx, seckey); |
648 | 0 | } |
649 | | |
650 | 0 | int secp256k1_ec_pubkey_negate(const secp256k1_context* ctx, secp256k1_pubkey *pubkey) { |
651 | 0 | int ret = 0; |
652 | 0 | secp256k1_ge p; |
653 | 0 | VERIFY_CHECK(ctx != NULL); |
654 | 0 | ARG_CHECK(pubkey != NULL); |
655 | | |
656 | 0 | ret = secp256k1_pubkey_load(ctx, &p, pubkey); |
657 | 0 | memset(pubkey, 0, sizeof(*pubkey)); |
658 | 0 | if (ret) { |
659 | 0 | secp256k1_ge_neg(&p, &p); |
660 | 0 | secp256k1_pubkey_save(pubkey, &p); |
661 | 0 | } |
662 | 0 | return ret; |
663 | 0 | } |
664 | | |
665 | | |
666 | 141k | static int secp256k1_ec_seckey_tweak_add_helper(secp256k1_scalar *sec, const unsigned char *tweak32) { |
667 | 141k | secp256k1_scalar term; |
668 | 141k | int overflow = 0; |
669 | 141k | int ret = 0; |
670 | | |
671 | 141k | secp256k1_scalar_set_b32(&term, tweak32, &overflow); |
672 | 141k | ret = (!overflow) & secp256k1_eckey_privkey_tweak_add(sec, &term); |
673 | 141k | secp256k1_scalar_clear(&term); |
674 | 141k | return ret; |
675 | 141k | } |
676 | | |
677 | 141k | int secp256k1_ec_seckey_tweak_add(const secp256k1_context* ctx, unsigned char *seckey, const unsigned char *tweak32) { |
678 | 141k | secp256k1_scalar sec; |
679 | 141k | int ret = 0; |
680 | 141k | VERIFY_CHECK(ctx != NULL); |
681 | 141k | ARG_CHECK(seckey != NULL); |
682 | 141k | ARG_CHECK(tweak32 != NULL); |
683 | | |
684 | 141k | ret = secp256k1_scalar_set_b32_seckey(&sec, seckey); |
685 | 141k | ret &= secp256k1_ec_seckey_tweak_add_helper(&sec, tweak32); |
686 | 141k | secp256k1_scalar_cmov(&sec, &secp256k1_scalar_zero, !ret); |
687 | 141k | secp256k1_scalar_get_b32(seckey, &sec); |
688 | | |
689 | 141k | secp256k1_scalar_clear(&sec); |
690 | 141k | return ret; |
691 | 141k | } |
692 | | |
693 | 0 | int secp256k1_ec_privkey_tweak_add(const secp256k1_context* ctx, unsigned char *seckey, const unsigned char *tweak32) { |
694 | 0 | return secp256k1_ec_seckey_tweak_add(ctx, seckey, tweak32); |
695 | 0 | } |
696 | | |
697 | 3.27M | static int secp256k1_ec_pubkey_tweak_add_helper(secp256k1_ge *p, const unsigned char *tweak32) { |
698 | 3.27M | secp256k1_scalar term; |
699 | 3.27M | int overflow = 0; |
700 | 3.27M | secp256k1_scalar_set_b32(&term, tweak32, &overflow); |
701 | 3.27M | return !overflow && secp256k1_eckey_pubkey_tweak_add(p, &term); |
702 | 3.27M | } |
703 | | |
704 | 2.29M | int secp256k1_ec_pubkey_tweak_add(const secp256k1_context* ctx, secp256k1_pubkey *pubkey, const unsigned char *tweak32) { |
705 | 2.29M | secp256k1_ge p; |
706 | 2.29M | int ret = 0; |
707 | 2.29M | VERIFY_CHECK(ctx != NULL); |
708 | 2.29M | ARG_CHECK(pubkey != NULL); |
709 | 2.29M | ARG_CHECK(tweak32 != NULL); |
710 | | |
711 | 2.29M | ret = secp256k1_pubkey_load(ctx, &p, pubkey); |
712 | 2.29M | memset(pubkey, 0, sizeof(*pubkey)); |
713 | 2.29M | ret = ret && secp256k1_ec_pubkey_tweak_add_helper(&p, tweak32); |
714 | 2.29M | if (ret) { |
715 | 2.29M | secp256k1_pubkey_save(pubkey, &p); |
716 | 2.29M | } |
717 | | |
718 | 2.29M | return ret; |
719 | 2.29M | } |
720 | | |
721 | 0 | int secp256k1_ec_seckey_tweak_mul(const secp256k1_context* ctx, unsigned char *seckey, const unsigned char *tweak32) { |
722 | 0 | secp256k1_scalar factor; |
723 | 0 | secp256k1_scalar sec; |
724 | 0 | int ret = 0; |
725 | 0 | int overflow = 0; |
726 | 0 | VERIFY_CHECK(ctx != NULL); |
727 | 0 | ARG_CHECK(seckey != NULL); |
728 | 0 | ARG_CHECK(tweak32 != NULL); |
729 | | |
730 | 0 | secp256k1_scalar_set_b32(&factor, tweak32, &overflow); |
731 | 0 | ret = secp256k1_scalar_set_b32_seckey(&sec, seckey); |
732 | 0 | ret &= (!overflow) & secp256k1_eckey_privkey_tweak_mul(&sec, &factor); |
733 | 0 | secp256k1_scalar_cmov(&sec, &secp256k1_scalar_zero, !ret); |
734 | 0 | secp256k1_scalar_get_b32(seckey, &sec); |
735 | |
|
736 | 0 | secp256k1_scalar_clear(&sec); |
737 | 0 | secp256k1_scalar_clear(&factor); |
738 | 0 | return ret; |
739 | 0 | } |
740 | | |
741 | 0 | int secp256k1_ec_privkey_tweak_mul(const secp256k1_context* ctx, unsigned char *seckey, const unsigned char *tweak32) { |
742 | 0 | return secp256k1_ec_seckey_tweak_mul(ctx, seckey, tweak32); |
743 | 0 | } |
744 | | |
745 | 0 | int secp256k1_ec_pubkey_tweak_mul(const secp256k1_context* ctx, secp256k1_pubkey *pubkey, const unsigned char *tweak32) { |
746 | 0 | secp256k1_ge p; |
747 | 0 | secp256k1_scalar factor; |
748 | 0 | int ret = 0; |
749 | 0 | int overflow = 0; |
750 | 0 | VERIFY_CHECK(ctx != NULL); |
751 | 0 | ARG_CHECK(pubkey != NULL); |
752 | 0 | ARG_CHECK(tweak32 != NULL); |
753 | | |
754 | 0 | secp256k1_scalar_set_b32(&factor, tweak32, &overflow); |
755 | 0 | ret = !overflow && secp256k1_pubkey_load(ctx, &p, pubkey); |
756 | 0 | memset(pubkey, 0, sizeof(*pubkey)); |
757 | 0 | if (ret) { |
758 | 0 | if (secp256k1_eckey_pubkey_tweak_mul(&p, &factor)) { |
759 | 0 | secp256k1_pubkey_save(pubkey, &p); |
760 | 0 | } else { |
761 | 0 | ret = 0; |
762 | 0 | } |
763 | 0 | } |
764 | |
|
765 | 0 | return ret; |
766 | 0 | } |
767 | | |
768 | 8.61k | int secp256k1_context_randomize(secp256k1_context* ctx, const unsigned char *seed32) { |
769 | 8.61k | VERIFY_CHECK(ctx != NULL); |
770 | 8.61k | ARG_CHECK(secp256k1_context_is_proper(ctx)); |
771 | | |
772 | 8.61k | if (secp256k1_ecmult_gen_context_is_built(&ctx->ecmult_gen_ctx)) { |
773 | 8.61k | secp256k1_ecmult_gen_blind(&ctx->ecmult_gen_ctx, seed32); |
774 | 8.61k | } |
775 | 8.61k | return 1; |
776 | 8.61k | } |
777 | | |
778 | 0 | int secp256k1_ec_pubkey_combine(const secp256k1_context* ctx, secp256k1_pubkey *pubnonce, const secp256k1_pubkey * const *pubnonces, size_t n) { |
779 | 0 | size_t i; |
780 | 0 | secp256k1_gej Qj; |
781 | 0 | secp256k1_ge Q; |
782 | |
|
783 | 0 | VERIFY_CHECK(ctx != NULL); |
784 | 0 | ARG_CHECK(pubnonce != NULL); |
785 | 0 | memset(pubnonce, 0, sizeof(*pubnonce)); |
786 | 0 | ARG_CHECK(n >= 1); |
787 | 0 | ARG_CHECK(pubnonces != NULL); |
788 | | |
789 | 0 | secp256k1_gej_set_infinity(&Qj); |
790 | |
|
791 | 0 | for (i = 0; i < n; i++) { |
792 | 0 | ARG_CHECK(pubnonces[i] != NULL); |
793 | 0 | secp256k1_pubkey_load(ctx, &Q, pubnonces[i]); |
794 | 0 | secp256k1_gej_add_ge(&Qj, &Qj, &Q); |
795 | 0 | } |
796 | 0 | if (secp256k1_gej_is_infinity(&Qj)) { |
797 | 0 | return 0; |
798 | 0 | } |
799 | 0 | secp256k1_ge_set_gej(&Q, &Qj); |
800 | 0 | secp256k1_pubkey_save(pubnonce, &Q); |
801 | 0 | return 1; |
802 | 0 | } |
803 | | |
804 | 0 | int secp256k1_tagged_sha256(const secp256k1_context* ctx, unsigned char *hash32, const unsigned char *tag, size_t taglen, const unsigned char *msg, size_t msglen) { |
805 | 0 | secp256k1_sha256 sha; |
806 | 0 | VERIFY_CHECK(ctx != NULL); |
807 | 0 | ARG_CHECK(hash32 != NULL); |
808 | 0 | ARG_CHECK(tag != NULL); |
809 | 0 | ARG_CHECK(msg != NULL); |
810 | | |
811 | 0 | secp256k1_sha256_initialize_tagged(&sha, tag, taglen); |
812 | 0 | secp256k1_sha256_write(&sha, msg, msglen); |
813 | 0 | secp256k1_sha256_finalize(&sha, hash32); |
814 | 0 | return 1; |
815 | 0 | } |
816 | | |
817 | | #ifdef ENABLE_MODULE_ECDH |
818 | | # include "modules/ecdh/main_impl.h" |
819 | | #endif |
820 | | |
821 | | #ifdef ENABLE_MODULE_RECOVERY |
822 | | # include "modules/recovery/main_impl.h" |
823 | | #endif |
824 | | |
825 | | #ifdef ENABLE_MODULE_EXTRAKEYS |
826 | | # include "modules/extrakeys/main_impl.h" |
827 | | #endif |
828 | | |
829 | | #ifdef ENABLE_MODULE_SCHNORRSIG |
830 | | # include "modules/schnorrsig/main_impl.h" |
831 | | #endif |
832 | | |
833 | | #ifdef ENABLE_MODULE_ELLSWIFT |
834 | | # include "modules/ellswift/main_impl.h" |
835 | | #endif |