1 /*
2  *  Elliptic curve DSA
3  *
4  *  Copyright The Mbed TLS Contributors
5  *  SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later
6  */
7 
8 /*
9  * References:
10  *
11  * SEC1 https://www.secg.org/sec1-v2.pdf
12  */
13 
14 #include "common.h"
15 
16 #if defined(MBEDTLS_ECDSA_C)
17 
18 #include "mbedtls/ecdsa.h"
19 #include "mbedtls/asn1write.h"
20 
21 #include <string.h>
22 
23 #if defined(MBEDTLS_ECDSA_DETERMINISTIC)
24 #include "mbedtls/hmac_drbg.h"
25 #endif
26 
27 #include "mbedtls/platform.h"
28 
29 #include "mbedtls/platform_util.h"
30 #include "mbedtls/error.h"
31 
32 #if defined(MBEDTLS_ECP_RESTARTABLE)
33 
34 /*
35  * Sub-context for ecdsa_verify()
36  */
37 struct mbedtls_ecdsa_restart_ver {
38     mbedtls_mpi u1, u2;     /* intermediate values  */
39     enum {                  /* what to do next?     */
40         ecdsa_ver_init = 0, /* getting started      */
41         ecdsa_ver_muladd,   /* muladd step          */
42     } state;
43 };
44 
45 /*
46  * Init verify restart sub-context
47  */
ecdsa_restart_ver_init(mbedtls_ecdsa_restart_ver_ctx * ctx)48 static void ecdsa_restart_ver_init(mbedtls_ecdsa_restart_ver_ctx *ctx)
49 {
50     mbedtls_mpi_init(&ctx->u1);
51     mbedtls_mpi_init(&ctx->u2);
52     ctx->state = ecdsa_ver_init;
53 }
54 
55 /*
56  * Free the components of a verify restart sub-context
57  */
ecdsa_restart_ver_free(mbedtls_ecdsa_restart_ver_ctx * ctx)58 static void ecdsa_restart_ver_free(mbedtls_ecdsa_restart_ver_ctx *ctx)
59 {
60     if (ctx == NULL) {
61         return;
62     }
63 
64     mbedtls_mpi_free(&ctx->u1);
65     mbedtls_mpi_free(&ctx->u2);
66 
67     ecdsa_restart_ver_init(ctx);
68 }
69 
70 /*
71  * Sub-context for ecdsa_sign()
72  */
73 struct mbedtls_ecdsa_restart_sig {
74     int sign_tries;
75     int key_tries;
76     mbedtls_mpi k;          /* per-signature random */
77     mbedtls_mpi r;          /* r value              */
78     enum {                  /* what to do next?     */
79         ecdsa_sig_init = 0, /* getting started      */
80         ecdsa_sig_mul,      /* doing ecp_mul()      */
81         ecdsa_sig_modn,     /* mod N computations   */
82     } state;
83 };
84 
85 /*
86  * Init verify sign sub-context
87  */
ecdsa_restart_sig_init(mbedtls_ecdsa_restart_sig_ctx * ctx)88 static void ecdsa_restart_sig_init(mbedtls_ecdsa_restart_sig_ctx *ctx)
89 {
90     ctx->sign_tries = 0;
91     ctx->key_tries = 0;
92     mbedtls_mpi_init(&ctx->k);
93     mbedtls_mpi_init(&ctx->r);
94     ctx->state = ecdsa_sig_init;
95 }
96 
97 /*
98  * Free the components of a sign restart sub-context
99  */
ecdsa_restart_sig_free(mbedtls_ecdsa_restart_sig_ctx * ctx)100 static void ecdsa_restart_sig_free(mbedtls_ecdsa_restart_sig_ctx *ctx)
101 {
102     if (ctx == NULL) {
103         return;
104     }
105 
106     mbedtls_mpi_free(&ctx->k);
107     mbedtls_mpi_free(&ctx->r);
108 }
109 
110 #if defined(MBEDTLS_ECDSA_DETERMINISTIC)
111 /*
112  * Sub-context for ecdsa_sign_det()
113  */
114 struct mbedtls_ecdsa_restart_det {
115     mbedtls_hmac_drbg_context rng_ctx;  /* DRBG state   */
116     enum {                      /* what to do next?     */
117         ecdsa_det_init = 0,     /* getting started      */
118         ecdsa_det_sign,         /* make signature       */
119     } state;
120 };
121 
122 /*
123  * Init verify sign_det sub-context
124  */
ecdsa_restart_det_init(mbedtls_ecdsa_restart_det_ctx * ctx)125 static void ecdsa_restart_det_init(mbedtls_ecdsa_restart_det_ctx *ctx)
126 {
127     mbedtls_hmac_drbg_init(&ctx->rng_ctx);
128     ctx->state = ecdsa_det_init;
129 }
130 
131 /*
132  * Free the components of a sign_det restart sub-context
133  */
ecdsa_restart_det_free(mbedtls_ecdsa_restart_det_ctx * ctx)134 static void ecdsa_restart_det_free(mbedtls_ecdsa_restart_det_ctx *ctx)
135 {
136     if (ctx == NULL) {
137         return;
138     }
139 
140     mbedtls_hmac_drbg_free(&ctx->rng_ctx);
141 
142     ecdsa_restart_det_init(ctx);
143 }
144 #endif /* MBEDTLS_ECDSA_DETERMINISTIC */
145 
146 #define ECDSA_RS_ECP    (rs_ctx == NULL ? NULL : &rs_ctx->ecp)
147 
148 /* Utility macro for checking and updating ops budget */
149 #define ECDSA_BUDGET(ops)   \
150     MBEDTLS_MPI_CHK(mbedtls_ecp_check_budget(grp, ECDSA_RS_ECP, ops));
151 
152 /* Call this when entering a function that needs its own sub-context */
153 #define ECDSA_RS_ENTER(SUB)   do {                                 \
154         /* reset ops count for this call if top-level */                 \
155         if (rs_ctx != NULL && rs_ctx->ecp.depth++ == 0)                 \
156         rs_ctx->ecp.ops_done = 0;                                    \
157                                                                      \
158         /* set up our own sub-context if needed */                       \
159         if (mbedtls_ecp_restart_is_enabled() &&                          \
160             rs_ctx != NULL && rs_ctx->SUB == NULL)                      \
161         {                                                                \
162             rs_ctx->SUB = mbedtls_calloc(1, sizeof(*rs_ctx->SUB));   \
163             if (rs_ctx->SUB == NULL)                                    \
164             return MBEDTLS_ERR_ECP_ALLOC_FAILED;                  \
165                                                                    \
166             ecdsa_restart_## SUB ##_init(rs_ctx->SUB);                 \
167         }                                                                \
168 } while (0)
169 
170 /* Call this when leaving a function that needs its own sub-context */
171 #define ECDSA_RS_LEAVE(SUB)   do {                                 \
172         /* clear our sub-context when not in progress (done or error) */ \
173         if (rs_ctx != NULL && rs_ctx->SUB != NULL &&                     \
174             ret != MBEDTLS_ERR_ECP_IN_PROGRESS)                         \
175         {                                                                \
176             ecdsa_restart_## SUB ##_free(rs_ctx->SUB);                 \
177             mbedtls_free(rs_ctx->SUB);                                 \
178             rs_ctx->SUB = NULL;                                          \
179         }                                                                \
180                                                                      \
181         if (rs_ctx != NULL)                                             \
182         rs_ctx->ecp.depth--;                                         \
183 } while (0)
184 
185 #else /* MBEDTLS_ECP_RESTARTABLE */
186 
187 #define ECDSA_RS_ECP    NULL
188 
189 #define ECDSA_BUDGET(ops)     /* no-op; for compatibility */
190 
191 #define ECDSA_RS_ENTER(SUB)   (void) rs_ctx
192 #define ECDSA_RS_LEAVE(SUB)   (void) rs_ctx
193 
194 #endif /* MBEDTLS_ECP_RESTARTABLE */
195 
196 #if defined(MBEDTLS_ECDSA_DETERMINISTIC) || \
197     !defined(MBEDTLS_ECDSA_SIGN_ALT)     || \
198     !defined(MBEDTLS_ECDSA_VERIFY_ALT)
199 /*
200  * Derive a suitable integer for group grp from a buffer of length len
201  * SEC1 4.1.3 step 5 aka SEC1 4.1.4 step 3
202  */
derive_mpi(const mbedtls_ecp_group * grp,mbedtls_mpi * x,const unsigned char * buf,size_t blen)203 static int derive_mpi(const mbedtls_ecp_group *grp, mbedtls_mpi *x,
204                       const unsigned char *buf, size_t blen)
205 {
206     int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
207     size_t n_size = (grp->nbits + 7) / 8;
208     size_t use_size = blen > n_size ? n_size : blen;
209 
210     MBEDTLS_MPI_CHK(mbedtls_mpi_read_binary(x, buf, use_size));
211     if (use_size * 8 > grp->nbits) {
212         MBEDTLS_MPI_CHK(mbedtls_mpi_shift_r(x, use_size * 8 - grp->nbits));
213     }
214 
215     /* While at it, reduce modulo N */
216     if (mbedtls_mpi_cmp_mpi(x, &grp->N) >= 0) {
217         MBEDTLS_MPI_CHK(mbedtls_mpi_sub_mpi(x, x, &grp->N));
218     }
219 
220 cleanup:
221     return ret;
222 }
223 #endif /* ECDSA_DETERMINISTIC || !ECDSA_SIGN_ALT || !ECDSA_VERIFY_ALT */
224 
mbedtls_ecdsa_can_do(mbedtls_ecp_group_id gid)225 int mbedtls_ecdsa_can_do(mbedtls_ecp_group_id gid)
226 {
227     switch (gid) {
228 #ifdef MBEDTLS_ECP_DP_CURVE25519_ENABLED
229         case MBEDTLS_ECP_DP_CURVE25519: return 0;
230 #endif
231 #ifdef MBEDTLS_ECP_DP_CURVE448_ENABLED
232         case MBEDTLS_ECP_DP_CURVE448: return 0;
233 #endif
234         default: return 1;
235     }
236 }
237 
238 #if !defined(MBEDTLS_ECDSA_SIGN_ALT)
239 /*
240  * Compute ECDSA signature of a hashed message (SEC1 4.1.3)
241  * Obviously, compared to SEC1 4.1.3, we skip step 4 (hash message)
242  */
mbedtls_ecdsa_sign_restartable(mbedtls_ecp_group * grp,mbedtls_mpi * r,mbedtls_mpi * s,const mbedtls_mpi * d,const unsigned char * buf,size_t blen,int (* f_rng)(void *,unsigned char *,size_t),void * p_rng,int (* f_rng_blind)(void *,unsigned char *,size_t),void * p_rng_blind,mbedtls_ecdsa_restart_ctx * rs_ctx)243 int mbedtls_ecdsa_sign_restartable(mbedtls_ecp_group *grp,
244                                    mbedtls_mpi *r, mbedtls_mpi *s,
245                                    const mbedtls_mpi *d, const unsigned char *buf, size_t blen,
246                                    int (*f_rng)(void *, unsigned char *, size_t), void *p_rng,
247                                    int (*f_rng_blind)(void *, unsigned char *, size_t),
248                                    void *p_rng_blind,
249                                    mbedtls_ecdsa_restart_ctx *rs_ctx)
250 {
251     int ret, key_tries, sign_tries;
252     int *p_sign_tries = &sign_tries, *p_key_tries = &key_tries;
253     mbedtls_ecp_point R;
254     mbedtls_mpi k, e, t;
255     mbedtls_mpi *pk = &k, *pr = r;
256 
257     /* Fail cleanly on curves such as Curve25519 that can't be used for ECDSA */
258     if (!mbedtls_ecdsa_can_do(grp->id) || grp->N.p == NULL) {
259         return MBEDTLS_ERR_ECP_BAD_INPUT_DATA;
260     }
261 
262     /* Make sure d is in range 1..n-1 */
263     if (mbedtls_mpi_cmp_int(d, 1) < 0 || mbedtls_mpi_cmp_mpi(d, &grp->N) >= 0) {
264         return MBEDTLS_ERR_ECP_INVALID_KEY;
265     }
266 
267     mbedtls_ecp_point_init(&R);
268     mbedtls_mpi_init(&k); mbedtls_mpi_init(&e); mbedtls_mpi_init(&t);
269 
270     ECDSA_RS_ENTER(sig);
271 
272 #if defined(MBEDTLS_ECP_RESTARTABLE)
273     if (rs_ctx != NULL && rs_ctx->sig != NULL) {
274         /* redirect to our context */
275         p_sign_tries = &rs_ctx->sig->sign_tries;
276         p_key_tries = &rs_ctx->sig->key_tries;
277         pk = &rs_ctx->sig->k;
278         pr = &rs_ctx->sig->r;
279 
280         /* jump to current step */
281         if (rs_ctx->sig->state == ecdsa_sig_mul) {
282             goto mul;
283         }
284         if (rs_ctx->sig->state == ecdsa_sig_modn) {
285             goto modn;
286         }
287     }
288 #endif /* MBEDTLS_ECP_RESTARTABLE */
289 
290     *p_sign_tries = 0;
291     do {
292         if ((*p_sign_tries)++ > 10) {
293             ret = MBEDTLS_ERR_ECP_RANDOM_FAILED;
294             goto cleanup;
295         }
296 
297         /*
298          * Steps 1-3: generate a suitable ephemeral keypair
299          * and set r = xR mod n
300          */
301         *p_key_tries = 0;
302         do {
303             if ((*p_key_tries)++ > 10) {
304                 ret = MBEDTLS_ERR_ECP_RANDOM_FAILED;
305                 goto cleanup;
306             }
307 
308             MBEDTLS_MPI_CHK(mbedtls_ecp_gen_privkey(grp, pk, f_rng, p_rng));
309 
310 #if defined(MBEDTLS_ECP_RESTARTABLE)
311             if (rs_ctx != NULL && rs_ctx->sig != NULL) {
312                 rs_ctx->sig->state = ecdsa_sig_mul;
313             }
314 
315 mul:
316 #endif
317             MBEDTLS_MPI_CHK(mbedtls_ecp_mul_restartable(grp, &R, pk, &grp->G,
318                                                         f_rng_blind,
319                                                         p_rng_blind,
320                                                         ECDSA_RS_ECP));
321             MBEDTLS_MPI_CHK(mbedtls_mpi_mod_mpi(pr, &R.X, &grp->N));
322         } while (mbedtls_mpi_cmp_int(pr, 0) == 0);
323 
324 #if defined(MBEDTLS_ECP_RESTARTABLE)
325         if (rs_ctx != NULL && rs_ctx->sig != NULL) {
326             rs_ctx->sig->state = ecdsa_sig_modn;
327         }
328 
329 modn:
330 #endif
331         /*
332          * Accounting for everything up to the end of the loop
333          * (step 6, but checking now avoids saving e and t)
334          */
335         ECDSA_BUDGET(MBEDTLS_ECP_OPS_INV + 4);
336 
337         /*
338          * Step 5: derive MPI from hashed message
339          */
340         MBEDTLS_MPI_CHK(derive_mpi(grp, &e, buf, blen));
341 
342         /*
343          * Generate a random value to blind inv_mod in next step,
344          * avoiding a potential timing leak.
345          */
346         MBEDTLS_MPI_CHK(mbedtls_ecp_gen_privkey(grp, &t, f_rng_blind,
347                                                 p_rng_blind));
348 
349         /*
350          * Step 6: compute s = (e + r * d) / k = t (e + rd) / (kt) mod n
351          */
352         MBEDTLS_MPI_CHK(mbedtls_mpi_mul_mpi(s, pr, d));
353         MBEDTLS_MPI_CHK(mbedtls_mpi_add_mpi(&e, &e, s));
354         MBEDTLS_MPI_CHK(mbedtls_mpi_mul_mpi(&e, &e, &t));
355         MBEDTLS_MPI_CHK(mbedtls_mpi_mul_mpi(pk, pk, &t));
356         MBEDTLS_MPI_CHK(mbedtls_mpi_mod_mpi(pk, pk, &grp->N));
357         MBEDTLS_MPI_CHK(mbedtls_mpi_inv_mod(s, pk, &grp->N));
358         MBEDTLS_MPI_CHK(mbedtls_mpi_mul_mpi(s, s, &e));
359         MBEDTLS_MPI_CHK(mbedtls_mpi_mod_mpi(s, s, &grp->N));
360     } while (mbedtls_mpi_cmp_int(s, 0) == 0);
361 
362 #if defined(MBEDTLS_ECP_RESTARTABLE)
363     if (rs_ctx != NULL && rs_ctx->sig != NULL) {
364         MBEDTLS_MPI_CHK(mbedtls_mpi_copy(r, pr));
365     }
366 #endif
367 
368 cleanup:
369     mbedtls_ecp_point_free(&R);
370     mbedtls_mpi_free(&k); mbedtls_mpi_free(&e); mbedtls_mpi_free(&t);
371 
372     ECDSA_RS_LEAVE(sig);
373 
374     return ret;
375 }
376 
377 /*
378  * Compute ECDSA signature of a hashed message
379  */
mbedtls_ecdsa_sign(mbedtls_ecp_group * grp,mbedtls_mpi * r,mbedtls_mpi * s,const mbedtls_mpi * d,const unsigned char * buf,size_t blen,int (* f_rng)(void *,unsigned char *,size_t),void * p_rng)380 int mbedtls_ecdsa_sign(mbedtls_ecp_group *grp, mbedtls_mpi *r, mbedtls_mpi *s,
381                        const mbedtls_mpi *d, const unsigned char *buf, size_t blen,
382                        int (*f_rng)(void *, unsigned char *, size_t), void *p_rng)
383 {
384     /* Use the same RNG for both blinding and ephemeral key generation */
385     return mbedtls_ecdsa_sign_restartable(grp, r, s, d, buf, blen,
386                                           f_rng, p_rng, f_rng, p_rng, NULL);
387 }
388 #endif /* !MBEDTLS_ECDSA_SIGN_ALT */
389 
390 #if defined(MBEDTLS_ECDSA_DETERMINISTIC)
391 /*
392  * Deterministic signature wrapper
393  *
394  * note:    The f_rng_blind parameter must not be NULL.
395  *
396  */
mbedtls_ecdsa_sign_det_restartable(mbedtls_ecp_group * grp,mbedtls_mpi * r,mbedtls_mpi * s,const mbedtls_mpi * d,const unsigned char * buf,size_t blen,mbedtls_md_type_t md_alg,int (* f_rng_blind)(void *,unsigned char *,size_t),void * p_rng_blind,mbedtls_ecdsa_restart_ctx * rs_ctx)397 int mbedtls_ecdsa_sign_det_restartable(mbedtls_ecp_group *grp,
398                                        mbedtls_mpi *r, mbedtls_mpi *s,
399                                        const mbedtls_mpi *d, const unsigned char *buf, size_t blen,
400                                        mbedtls_md_type_t md_alg,
401                                        int (*f_rng_blind)(void *, unsigned char *, size_t),
402                                        void *p_rng_blind,
403                                        mbedtls_ecdsa_restart_ctx *rs_ctx)
404 {
405     int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
406     mbedtls_hmac_drbg_context rng_ctx;
407     mbedtls_hmac_drbg_context *p_rng = &rng_ctx;
408     unsigned char data[2 * MBEDTLS_ECP_MAX_BYTES];
409     size_t grp_len = (grp->nbits + 7) / 8;
410     const mbedtls_md_info_t *md_info;
411     mbedtls_mpi h;
412 
413     if ((md_info = mbedtls_md_info_from_type(md_alg)) == NULL) {
414         return MBEDTLS_ERR_ECP_BAD_INPUT_DATA;
415     }
416 
417     mbedtls_mpi_init(&h);
418     mbedtls_hmac_drbg_init(&rng_ctx);
419 
420     ECDSA_RS_ENTER(det);
421 
422 #if defined(MBEDTLS_ECP_RESTARTABLE)
423     if (rs_ctx != NULL && rs_ctx->det != NULL) {
424         /* redirect to our context */
425         p_rng = &rs_ctx->det->rng_ctx;
426 
427         /* jump to current step */
428         if (rs_ctx->det->state == ecdsa_det_sign) {
429             goto sign;
430         }
431     }
432 #endif /* MBEDTLS_ECP_RESTARTABLE */
433 
434     /* Use private key and message hash (reduced) to initialize HMAC_DRBG */
435     MBEDTLS_MPI_CHK(mbedtls_mpi_write_binary(d, data, grp_len));
436     MBEDTLS_MPI_CHK(derive_mpi(grp, &h, buf, blen));
437     MBEDTLS_MPI_CHK(mbedtls_mpi_write_binary(&h, data + grp_len, grp_len));
438     MBEDTLS_MPI_CHK(mbedtls_hmac_drbg_seed_buf(p_rng, md_info, data, 2 * grp_len));
439 
440 #if defined(MBEDTLS_ECP_RESTARTABLE)
441     if (rs_ctx != NULL && rs_ctx->det != NULL) {
442         rs_ctx->det->state = ecdsa_det_sign;
443     }
444 
445 sign:
446 #endif
447 #if defined(MBEDTLS_ECDSA_SIGN_ALT)
448     (void) f_rng_blind;
449     (void) p_rng_blind;
450     ret = mbedtls_ecdsa_sign(grp, r, s, d, buf, blen,
451                              mbedtls_hmac_drbg_random, p_rng);
452 #else
453     ret = mbedtls_ecdsa_sign_restartable(grp, r, s, d, buf, blen,
454                                          mbedtls_hmac_drbg_random, p_rng,
455                                          f_rng_blind, p_rng_blind, rs_ctx);
456 #endif /* MBEDTLS_ECDSA_SIGN_ALT */
457 
458 cleanup:
459     mbedtls_hmac_drbg_free(&rng_ctx);
460     mbedtls_mpi_free(&h);
461 
462     ECDSA_RS_LEAVE(det);
463 
464     return ret;
465 }
466 
467 /*
468  * Deterministic signature wrapper
469  */
mbedtls_ecdsa_sign_det_ext(mbedtls_ecp_group * grp,mbedtls_mpi * r,mbedtls_mpi * s,const mbedtls_mpi * d,const unsigned char * buf,size_t blen,mbedtls_md_type_t md_alg,int (* f_rng_blind)(void *,unsigned char *,size_t),void * p_rng_blind)470 int mbedtls_ecdsa_sign_det_ext(mbedtls_ecp_group *grp, mbedtls_mpi *r,
471                                mbedtls_mpi *s, const mbedtls_mpi *d,
472                                const unsigned char *buf, size_t blen,
473                                mbedtls_md_type_t md_alg,
474                                int (*f_rng_blind)(void *, unsigned char *,
475                                                   size_t),
476                                void *p_rng_blind)
477 {
478     return mbedtls_ecdsa_sign_det_restartable(grp, r, s, d, buf, blen, md_alg,
479                                               f_rng_blind, p_rng_blind, NULL);
480 }
481 #endif /* MBEDTLS_ECDSA_DETERMINISTIC */
482 
483 #if !defined(MBEDTLS_ECDSA_VERIFY_ALT)
484 /*
485  * Verify ECDSA signature of hashed message (SEC1 4.1.4)
486  * Obviously, compared to SEC1 4.1.3, we skip step 2 (hash message)
487  */
mbedtls_ecdsa_verify_restartable(mbedtls_ecp_group * grp,const unsigned char * buf,size_t blen,const mbedtls_ecp_point * Q,const mbedtls_mpi * r,const mbedtls_mpi * s,mbedtls_ecdsa_restart_ctx * rs_ctx)488 int mbedtls_ecdsa_verify_restartable(mbedtls_ecp_group *grp,
489                                      const unsigned char *buf, size_t blen,
490                                      const mbedtls_ecp_point *Q,
491                                      const mbedtls_mpi *r,
492                                      const mbedtls_mpi *s,
493                                      mbedtls_ecdsa_restart_ctx *rs_ctx)
494 {
495     int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
496     mbedtls_mpi e, s_inv, u1, u2;
497     mbedtls_ecp_point R;
498     mbedtls_mpi *pu1 = &u1, *pu2 = &u2;
499 
500     mbedtls_ecp_point_init(&R);
501     mbedtls_mpi_init(&e); mbedtls_mpi_init(&s_inv);
502     mbedtls_mpi_init(&u1); mbedtls_mpi_init(&u2);
503 
504     /* Fail cleanly on curves such as Curve25519 that can't be used for ECDSA */
505     if (!mbedtls_ecdsa_can_do(grp->id) || grp->N.p == NULL) {
506         return MBEDTLS_ERR_ECP_BAD_INPUT_DATA;
507     }
508 
509     ECDSA_RS_ENTER(ver);
510 
511 #if defined(MBEDTLS_ECP_RESTARTABLE)
512     if (rs_ctx != NULL && rs_ctx->ver != NULL) {
513         /* redirect to our context */
514         pu1 = &rs_ctx->ver->u1;
515         pu2 = &rs_ctx->ver->u2;
516 
517         /* jump to current step */
518         if (rs_ctx->ver->state == ecdsa_ver_muladd) {
519             goto muladd;
520         }
521     }
522 #endif /* MBEDTLS_ECP_RESTARTABLE */
523 
524     /*
525      * Step 1: make sure r and s are in range 1..n-1
526      */
527     if (mbedtls_mpi_cmp_int(r, 1) < 0 || mbedtls_mpi_cmp_mpi(r, &grp->N) >= 0 ||
528         mbedtls_mpi_cmp_int(s, 1) < 0 || mbedtls_mpi_cmp_mpi(s, &grp->N) >= 0) {
529         ret = MBEDTLS_ERR_ECP_VERIFY_FAILED;
530         goto cleanup;
531     }
532 
533     /*
534      * Step 3: derive MPI from hashed message
535      */
536     MBEDTLS_MPI_CHK(derive_mpi(grp, &e, buf, blen));
537 
538     /*
539      * Step 4: u1 = e / s mod n, u2 = r / s mod n
540      */
541     ECDSA_BUDGET(MBEDTLS_ECP_OPS_CHK + MBEDTLS_ECP_OPS_INV + 2);
542 
543     MBEDTLS_MPI_CHK(mbedtls_mpi_inv_mod(&s_inv, s, &grp->N));
544 
545     MBEDTLS_MPI_CHK(mbedtls_mpi_mul_mpi(pu1, &e, &s_inv));
546     MBEDTLS_MPI_CHK(mbedtls_mpi_mod_mpi(pu1, pu1, &grp->N));
547 
548     MBEDTLS_MPI_CHK(mbedtls_mpi_mul_mpi(pu2, r, &s_inv));
549     MBEDTLS_MPI_CHK(mbedtls_mpi_mod_mpi(pu2, pu2, &grp->N));
550 
551 #if defined(MBEDTLS_ECP_RESTARTABLE)
552     if (rs_ctx != NULL && rs_ctx->ver != NULL) {
553         rs_ctx->ver->state = ecdsa_ver_muladd;
554     }
555 
556 muladd:
557 #endif
558     /*
559      * Step 5: R = u1 G + u2 Q
560      */
561     MBEDTLS_MPI_CHK(mbedtls_ecp_muladd_restartable(grp,
562                                                    &R, pu1, &grp->G, pu2, Q, ECDSA_RS_ECP));
563 
564     if (mbedtls_ecp_is_zero(&R)) {
565         ret = MBEDTLS_ERR_ECP_VERIFY_FAILED;
566         goto cleanup;
567     }
568 
569     /*
570      * Step 6: convert xR to an integer (no-op)
571      * Step 7: reduce xR mod n (gives v)
572      */
573     MBEDTLS_MPI_CHK(mbedtls_mpi_mod_mpi(&R.X, &R.X, &grp->N));
574 
575     /*
576      * Step 8: check if v (that is, R.X) is equal to r
577      */
578     if (mbedtls_mpi_cmp_mpi(&R.X, r) != 0) {
579         ret = MBEDTLS_ERR_ECP_VERIFY_FAILED;
580         goto cleanup;
581     }
582 
583 cleanup:
584     mbedtls_ecp_point_free(&R);
585     mbedtls_mpi_free(&e); mbedtls_mpi_free(&s_inv);
586     mbedtls_mpi_free(&u1); mbedtls_mpi_free(&u2);
587 
588     ECDSA_RS_LEAVE(ver);
589 
590     return ret;
591 }
592 
593 /*
594  * Verify ECDSA signature of hashed message
595  */
mbedtls_ecdsa_verify(mbedtls_ecp_group * grp,const unsigned char * buf,size_t blen,const mbedtls_ecp_point * Q,const mbedtls_mpi * r,const mbedtls_mpi * s)596 int mbedtls_ecdsa_verify(mbedtls_ecp_group *grp,
597                          const unsigned char *buf, size_t blen,
598                          const mbedtls_ecp_point *Q,
599                          const mbedtls_mpi *r,
600                          const mbedtls_mpi *s)
601 {
602     return mbedtls_ecdsa_verify_restartable(grp, buf, blen, Q, r, s, NULL);
603 }
604 #endif /* !MBEDTLS_ECDSA_VERIFY_ALT */
605 
606 /*
607  * Convert a signature (given by context) to ASN.1
608  */
ecdsa_signature_to_asn1(const mbedtls_mpi * r,const mbedtls_mpi * s,unsigned char * sig,size_t sig_size,size_t * slen)609 static int ecdsa_signature_to_asn1(const mbedtls_mpi *r, const mbedtls_mpi *s,
610                                    unsigned char *sig, size_t sig_size,
611                                    size_t *slen)
612 {
613     int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
614     unsigned char buf[MBEDTLS_ECDSA_MAX_LEN] = { 0 };
615     unsigned char *p = buf + sizeof(buf);
616     size_t len = 0;
617 
618     MBEDTLS_ASN1_CHK_ADD(len, mbedtls_asn1_write_mpi(&p, buf, s));
619     MBEDTLS_ASN1_CHK_ADD(len, mbedtls_asn1_write_mpi(&p, buf, r));
620 
621     MBEDTLS_ASN1_CHK_ADD(len, mbedtls_asn1_write_len(&p, buf, len));
622     MBEDTLS_ASN1_CHK_ADD(len, mbedtls_asn1_write_tag(&p, buf,
623                                                      MBEDTLS_ASN1_CONSTRUCTED |
624                                                      MBEDTLS_ASN1_SEQUENCE));
625 
626     if (len > sig_size) {
627         return MBEDTLS_ERR_ECP_BUFFER_TOO_SMALL;
628     }
629 
630     memcpy(sig, p, len);
631     *slen = len;
632 
633     return 0;
634 }
635 
636 /*
637  * Compute and write signature
638  */
mbedtls_ecdsa_write_signature_restartable(mbedtls_ecdsa_context * ctx,mbedtls_md_type_t md_alg,const unsigned char * hash,size_t hlen,unsigned char * sig,size_t sig_size,size_t * slen,int (* f_rng)(void *,unsigned char *,size_t),void * p_rng,mbedtls_ecdsa_restart_ctx * rs_ctx)639 int mbedtls_ecdsa_write_signature_restartable(mbedtls_ecdsa_context *ctx,
640                                               mbedtls_md_type_t md_alg,
641                                               const unsigned char *hash, size_t hlen,
642                                               unsigned char *sig, size_t sig_size, size_t *slen,
643                                               int (*f_rng)(void *, unsigned char *, size_t),
644                                               void *p_rng,
645                                               mbedtls_ecdsa_restart_ctx *rs_ctx)
646 {
647     int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
648     mbedtls_mpi r, s;
649     if (f_rng == NULL) {
650         return MBEDTLS_ERR_ECP_BAD_INPUT_DATA;
651     }
652 
653     mbedtls_mpi_init(&r);
654     mbedtls_mpi_init(&s);
655 
656 #if defined(MBEDTLS_ECDSA_DETERMINISTIC)
657     MBEDTLS_MPI_CHK(mbedtls_ecdsa_sign_det_restartable(&ctx->grp, &r, &s, &ctx->d,
658                                                        hash, hlen, md_alg, f_rng,
659                                                        p_rng, rs_ctx));
660 #else
661     (void) md_alg;
662 
663 #if defined(MBEDTLS_ECDSA_SIGN_ALT)
664     (void) rs_ctx;
665 
666     MBEDTLS_MPI_CHK(mbedtls_ecdsa_sign(&ctx->grp, &r, &s, &ctx->d,
667                                        hash, hlen, f_rng, p_rng));
668 #else
669     /* Use the same RNG for both blinding and ephemeral key generation */
670     MBEDTLS_MPI_CHK(mbedtls_ecdsa_sign_restartable(&ctx->grp, &r, &s, &ctx->d,
671                                                    hash, hlen, f_rng, p_rng, f_rng,
672                                                    p_rng, rs_ctx));
673 #endif /* MBEDTLS_ECDSA_SIGN_ALT */
674 #endif /* MBEDTLS_ECDSA_DETERMINISTIC */
675 
676     MBEDTLS_MPI_CHK(ecdsa_signature_to_asn1(&r, &s, sig, sig_size, slen));
677 
678 cleanup:
679     mbedtls_mpi_free(&r);
680     mbedtls_mpi_free(&s);
681 
682     return ret;
683 }
684 
685 /*
686  * Compute and write signature
687  */
mbedtls_ecdsa_write_signature(mbedtls_ecdsa_context * ctx,mbedtls_md_type_t md_alg,const unsigned char * hash,size_t hlen,unsigned char * sig,size_t sig_size,size_t * slen,int (* f_rng)(void *,unsigned char *,size_t),void * p_rng)688 int mbedtls_ecdsa_write_signature(mbedtls_ecdsa_context *ctx,
689                                   mbedtls_md_type_t md_alg,
690                                   const unsigned char *hash, size_t hlen,
691                                   unsigned char *sig, size_t sig_size, size_t *slen,
692                                   int (*f_rng)(void *, unsigned char *, size_t),
693                                   void *p_rng)
694 {
695     return mbedtls_ecdsa_write_signature_restartable(
696         ctx, md_alg, hash, hlen, sig, sig_size, slen,
697         f_rng, p_rng, NULL);
698 }
699 
700 /*
701  * Read and check signature
702  */
mbedtls_ecdsa_read_signature(mbedtls_ecdsa_context * ctx,const unsigned char * hash,size_t hlen,const unsigned char * sig,size_t slen)703 int mbedtls_ecdsa_read_signature(mbedtls_ecdsa_context *ctx,
704                                  const unsigned char *hash, size_t hlen,
705                                  const unsigned char *sig, size_t slen)
706 {
707     return mbedtls_ecdsa_read_signature_restartable(
708         ctx, hash, hlen, sig, slen, NULL);
709 }
710 
711 /*
712  * Restartable read and check signature
713  */
mbedtls_ecdsa_read_signature_restartable(mbedtls_ecdsa_context * ctx,const unsigned char * hash,size_t hlen,const unsigned char * sig,size_t slen,mbedtls_ecdsa_restart_ctx * rs_ctx)714 int mbedtls_ecdsa_read_signature_restartable(mbedtls_ecdsa_context *ctx,
715                                              const unsigned char *hash, size_t hlen,
716                                              const unsigned char *sig, size_t slen,
717                                              mbedtls_ecdsa_restart_ctx *rs_ctx)
718 {
719     int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
720     unsigned char *p = (unsigned char *) sig;
721     const unsigned char *end = sig + slen;
722     size_t len;
723     mbedtls_mpi r, s;
724     mbedtls_mpi_init(&r);
725     mbedtls_mpi_init(&s);
726 
727     if ((ret = mbedtls_asn1_get_tag(&p, end, &len,
728                                     MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE)) != 0) {
729         ret += MBEDTLS_ERR_ECP_BAD_INPUT_DATA;
730         goto cleanup;
731     }
732 
733     if (p + len != end) {
734         ret = MBEDTLS_ERROR_ADD(MBEDTLS_ERR_ECP_BAD_INPUT_DATA,
735                                 MBEDTLS_ERR_ASN1_LENGTH_MISMATCH);
736         goto cleanup;
737     }
738 
739     if ((ret = mbedtls_asn1_get_mpi(&p, end, &r)) != 0 ||
740         (ret = mbedtls_asn1_get_mpi(&p, end, &s)) != 0) {
741         ret += MBEDTLS_ERR_ECP_BAD_INPUT_DATA;
742         goto cleanup;
743     }
744 #if defined(MBEDTLS_ECDSA_VERIFY_ALT)
745     (void) rs_ctx;
746 
747     if ((ret = mbedtls_ecdsa_verify(&ctx->grp, hash, hlen,
748                                     &ctx->Q, &r, &s)) != 0) {
749         goto cleanup;
750     }
751 #else
752     if ((ret = mbedtls_ecdsa_verify_restartable(&ctx->grp, hash, hlen,
753                                                 &ctx->Q, &r, &s, rs_ctx)) != 0) {
754         goto cleanup;
755     }
756 #endif /* MBEDTLS_ECDSA_VERIFY_ALT */
757 
758     /* At this point we know that the buffer starts with a valid signature.
759      * Return 0 if the buffer just contains the signature, and a specific
760      * error code if the valid signature is followed by more data. */
761     if (p != end) {
762         ret = MBEDTLS_ERR_ECP_SIG_LEN_MISMATCH;
763     }
764 
765 cleanup:
766     mbedtls_mpi_free(&r);
767     mbedtls_mpi_free(&s);
768 
769     return ret;
770 }
771 
772 #if !defined(MBEDTLS_ECDSA_GENKEY_ALT)
773 /*
774  * Generate key pair
775  */
mbedtls_ecdsa_genkey(mbedtls_ecdsa_context * ctx,mbedtls_ecp_group_id gid,int (* f_rng)(void *,unsigned char *,size_t),void * p_rng)776 int mbedtls_ecdsa_genkey(mbedtls_ecdsa_context *ctx, mbedtls_ecp_group_id gid,
777                          int (*f_rng)(void *, unsigned char *, size_t), void *p_rng)
778 {
779     int ret = 0;
780     ret = mbedtls_ecp_group_load(&ctx->grp, gid);
781     if (ret != 0) {
782         return ret;
783     }
784 
785     return mbedtls_ecp_gen_keypair(&ctx->grp, &ctx->d,
786                                    &ctx->Q, f_rng, p_rng);
787 }
788 #endif /* !MBEDTLS_ECDSA_GENKEY_ALT */
789 
790 /*
791  * Set context from an mbedtls_ecp_keypair
792  */
mbedtls_ecdsa_from_keypair(mbedtls_ecdsa_context * ctx,const mbedtls_ecp_keypair * key)793 int mbedtls_ecdsa_from_keypair(mbedtls_ecdsa_context *ctx, const mbedtls_ecp_keypair *key)
794 {
795     int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
796     if ((ret = mbedtls_ecp_group_copy(&ctx->grp, &key->grp)) != 0 ||
797         (ret = mbedtls_mpi_copy(&ctx->d, &key->d)) != 0 ||
798         (ret = mbedtls_ecp_copy(&ctx->Q, &key->Q)) != 0) {
799         mbedtls_ecdsa_free(ctx);
800     }
801 
802     return ret;
803 }
804 
805 /*
806  * Initialize context
807  */
mbedtls_ecdsa_init(mbedtls_ecdsa_context * ctx)808 void mbedtls_ecdsa_init(mbedtls_ecdsa_context *ctx)
809 {
810     mbedtls_ecp_keypair_init(ctx);
811 }
812 
813 /*
814  * Free context
815  */
mbedtls_ecdsa_free(mbedtls_ecdsa_context * ctx)816 void mbedtls_ecdsa_free(mbedtls_ecdsa_context *ctx)
817 {
818     if (ctx == NULL) {
819         return;
820     }
821 
822     mbedtls_ecp_keypair_free(ctx);
823 }
824 
825 #if defined(MBEDTLS_ECP_RESTARTABLE)
826 /*
827  * Initialize a restart context
828  */
mbedtls_ecdsa_restart_init(mbedtls_ecdsa_restart_ctx * ctx)829 void mbedtls_ecdsa_restart_init(mbedtls_ecdsa_restart_ctx *ctx)
830 {
831     mbedtls_ecp_restart_init(&ctx->ecp);
832 
833     ctx->ver = NULL;
834     ctx->sig = NULL;
835 #if defined(MBEDTLS_ECDSA_DETERMINISTIC)
836     ctx->det = NULL;
837 #endif
838 }
839 
840 /*
841  * Free the components of a restart context
842  */
mbedtls_ecdsa_restart_free(mbedtls_ecdsa_restart_ctx * ctx)843 void mbedtls_ecdsa_restart_free(mbedtls_ecdsa_restart_ctx *ctx)
844 {
845     if (ctx == NULL) {
846         return;
847     }
848 
849     mbedtls_ecp_restart_free(&ctx->ecp);
850 
851     ecdsa_restart_ver_free(ctx->ver);
852     mbedtls_free(ctx->ver);
853     ctx->ver = NULL;
854 
855     ecdsa_restart_sig_free(ctx->sig);
856     mbedtls_free(ctx->sig);
857     ctx->sig = NULL;
858 
859 #if defined(MBEDTLS_ECDSA_DETERMINISTIC)
860     ecdsa_restart_det_free(ctx->det);
861     mbedtls_free(ctx->det);
862     ctx->det = NULL;
863 #endif
864 }
865 #endif /* MBEDTLS_ECP_RESTARTABLE */
866 
867 #endif /* MBEDTLS_ECDSA_C */
868