2 * Copyright 2001-2018 The OpenSSL Project Authors. All Rights Reserved.
3 * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved
5 * Licensed under the Apache License 2.0 (the "License"). You may not use
6 * this file except in compliance with the License. You can obtain a copy
7 * in the file LICENSE in the source distribution or at
8 * https://www.openssl.org/source/license.html
12 * ECDSA low level APIs are deprecated for public use, but still ok for
15 #include "internal/deprecated.h"
19 #include <openssl/err.h>
20 #include <openssl/opensslv.h>
24 /* functions for EC_GROUP objects */
26 EC_GROUP
*EC_GROUP_new_ex(OPENSSL_CTX
*libctx
, const EC_METHOD
*meth
)
31 ECerr(EC_F_EC_GROUP_NEW_EX
, EC_R_SLOT_FULL
);
34 if (meth
->group_init
== 0) {
35 ECerr(EC_F_EC_GROUP_NEW_EX
, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
39 ret
= OPENSSL_zalloc(sizeof(*ret
));
41 ECerr(EC_F_EC_GROUP_NEW_EX
, ERR_R_MALLOC_FAILURE
);
47 if ((ret
->meth
->flags
& EC_FLAGS_CUSTOM_CURVE
) == 0) {
48 ret
->order
= BN_new();
49 if (ret
->order
== NULL
)
51 ret
->cofactor
= BN_new();
52 if (ret
->cofactor
== NULL
)
55 ret
->asn1_flag
= OPENSSL_EC_NAMED_CURVE
;
56 ret
->asn1_form
= POINT_CONVERSION_UNCOMPRESSED
;
57 if (!meth
->group_init(ret
))
63 BN_free(ret
->cofactor
);
69 EC_GROUP
*EC_GROUP_new(const EC_METHOD
*meth
)
71 return EC_GROUP_new_ex(NULL
, meth
);
75 void EC_pre_comp_free(EC_GROUP
*group
)
77 switch (group
->pre_comp_type
) {
81 #ifdef ECP_NISTZ256_ASM
82 EC_nistz256_pre_comp_free(group
->pre_comp
.nistz256
);
85 #ifndef OPENSSL_NO_EC_NISTP_64_GCC_128
87 EC_nistp224_pre_comp_free(group
->pre_comp
.nistp224
);
90 EC_nistp256_pre_comp_free(group
->pre_comp
.nistp256
);
93 EC_nistp521_pre_comp_free(group
->pre_comp
.nistp521
);
102 EC_ec_pre_comp_free(group
->pre_comp
.ec
);
105 group
->pre_comp
.ec
= NULL
;
108 void EC_GROUP_free(EC_GROUP
*group
)
113 if (group
->meth
->group_finish
!= 0)
114 group
->meth
->group_finish(group
);
116 EC_pre_comp_free(group
);
117 BN_MONT_CTX_free(group
->mont_data
);
118 EC_POINT_free(group
->generator
);
119 BN_free(group
->order
);
120 BN_free(group
->cofactor
);
121 OPENSSL_free(group
->seed
);
125 #ifndef OPENSSL_NO_DEPRECATED_3_0
126 void EC_GROUP_clear_free(EC_GROUP
*group
)
131 if (group
->meth
->group_clear_finish
!= 0)
132 group
->meth
->group_clear_finish(group
);
133 else if (group
->meth
->group_finish
!= 0)
134 group
->meth
->group_finish(group
);
136 EC_pre_comp_free(group
);
137 BN_MONT_CTX_free(group
->mont_data
);
138 EC_POINT_clear_free(group
->generator
);
139 BN_clear_free(group
->order
);
140 BN_clear_free(group
->cofactor
);
141 OPENSSL_clear_free(group
->seed
, group
->seed_len
);
142 OPENSSL_clear_free(group
, sizeof(*group
));
146 int EC_GROUP_copy(EC_GROUP
*dest
, const EC_GROUP
*src
)
148 if (dest
->meth
->group_copy
== 0) {
149 ECerr(EC_F_EC_GROUP_COPY
, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
152 if (dest
->meth
!= src
->meth
) {
153 ECerr(EC_F_EC_GROUP_COPY
, EC_R_INCOMPATIBLE_OBJECTS
);
159 dest
->libctx
= src
->libctx
;
160 dest
->curve_name
= src
->curve_name
;
162 /* Copy precomputed */
163 dest
->pre_comp_type
= src
->pre_comp_type
;
164 switch (src
->pre_comp_type
) {
166 dest
->pre_comp
.ec
= NULL
;
169 #ifdef ECP_NISTZ256_ASM
170 dest
->pre_comp
.nistz256
= EC_nistz256_pre_comp_dup(src
->pre_comp
.nistz256
);
173 #ifndef OPENSSL_NO_EC_NISTP_64_GCC_128
175 dest
->pre_comp
.nistp224
= EC_nistp224_pre_comp_dup(src
->pre_comp
.nistp224
);
178 dest
->pre_comp
.nistp256
= EC_nistp256_pre_comp_dup(src
->pre_comp
.nistp256
);
181 dest
->pre_comp
.nistp521
= EC_nistp521_pre_comp_dup(src
->pre_comp
.nistp521
);
190 dest
->pre_comp
.ec
= EC_ec_pre_comp_dup(src
->pre_comp
.ec
);
194 if (src
->mont_data
!= NULL
) {
195 if (dest
->mont_data
== NULL
) {
196 dest
->mont_data
= BN_MONT_CTX_new();
197 if (dest
->mont_data
== NULL
)
200 if (!BN_MONT_CTX_copy(dest
->mont_data
, src
->mont_data
))
203 /* src->generator == NULL */
204 BN_MONT_CTX_free(dest
->mont_data
);
205 dest
->mont_data
= NULL
;
208 if (src
->generator
!= NULL
) {
209 if (dest
->generator
== NULL
) {
210 dest
->generator
= EC_POINT_new(dest
);
211 if (dest
->generator
== NULL
)
214 if (!EC_POINT_copy(dest
->generator
, src
->generator
))
217 /* src->generator == NULL */
218 EC_POINT_clear_free(dest
->generator
);
219 dest
->generator
= NULL
;
222 if ((src
->meth
->flags
& EC_FLAGS_CUSTOM_CURVE
) == 0) {
223 if (!BN_copy(dest
->order
, src
->order
))
225 if (!BN_copy(dest
->cofactor
, src
->cofactor
))
229 dest
->asn1_flag
= src
->asn1_flag
;
230 dest
->asn1_form
= src
->asn1_form
;
233 OPENSSL_free(dest
->seed
);
234 if ((dest
->seed
= OPENSSL_malloc(src
->seed_len
)) == NULL
) {
235 ECerr(EC_F_EC_GROUP_COPY
, ERR_R_MALLOC_FAILURE
);
238 if (!memcpy(dest
->seed
, src
->seed
, src
->seed_len
))
240 dest
->seed_len
= src
->seed_len
;
242 OPENSSL_free(dest
->seed
);
247 return dest
->meth
->group_copy(dest
, src
);
250 EC_GROUP
*EC_GROUP_dup(const EC_GROUP
*a
)
258 if ((t
= EC_GROUP_new_ex(a
->libctx
, a
->meth
)) == NULL
)
260 if (!EC_GROUP_copy(t
, a
))
273 const EC_METHOD
*EC_GROUP_method_of(const EC_GROUP
*group
)
278 int EC_METHOD_get_field_type(const EC_METHOD
*meth
)
280 return meth
->field_type
;
283 static int ec_precompute_mont_data(EC_GROUP
*);
286 * Try computing cofactor from the generator order (n) and field cardinality (q).
287 * This works for all curves of cryptographic interest.
289 * Hasse thm: q + 1 - 2*sqrt(q) <= n*h <= q + 1 + 2*sqrt(q)
290 * h_min = (q + 1 - 2*sqrt(q))/n
291 * h_max = (q + 1 + 2*sqrt(q))/n
292 * h_max - h_min = 4*sqrt(q)/n
293 * So if n > 4*sqrt(q) holds, there is only one possible value for h:
294 * h = \lfloor (h_min + h_max)/2 \rceil = \lfloor (q + 1)/n \rceil
296 * Otherwise, zero cofactor and return success.
298 static int ec_guess_cofactor(EC_GROUP
*group
) {
304 * If the cofactor is too large, we cannot guess it.
305 * The RHS of below is a strict overestimate of lg(4 * sqrt(q))
307 if (BN_num_bits(group
->order
) <= (BN_num_bits(group
->field
) + 1) / 2 + 3) {
309 BN_zero(group
->cofactor
);
314 if ((ctx
= BN_CTX_new_ex(group
->libctx
)) == NULL
)
318 if ((q
= BN_CTX_get(ctx
)) == NULL
)
321 /* set q = 2**m for binary fields; q = p otherwise */
322 if (group
->meth
->field_type
== NID_X9_62_characteristic_two_field
) {
324 if (!BN_set_bit(q
, BN_num_bits(group
->field
) - 1))
327 if (!BN_copy(q
, group
->field
))
331 /* compute h = \lfloor (q + 1)/n \rceil = \lfloor (q + 1 + n/2)/n \rfloor */
332 if (!BN_rshift1(group
->cofactor
, group
->order
) /* n/2 */
333 || !BN_add(group
->cofactor
, group
->cofactor
, q
) /* q + n/2 */
335 || !BN_add(group
->cofactor
, group
->cofactor
, BN_value_one())
336 /* (q + 1 + n/2)/n */
337 || !BN_div(group
->cofactor
, NULL
, group
->cofactor
, group
->order
, ctx
))
346 int EC_GROUP_set_generator(EC_GROUP
*group
, const EC_POINT
*generator
,
347 const BIGNUM
*order
, const BIGNUM
*cofactor
)
349 if (generator
== NULL
) {
350 ECerr(EC_F_EC_GROUP_SET_GENERATOR
, ERR_R_PASSED_NULL_PARAMETER
);
354 /* require group->field >= 1 */
355 if (group
->field
== NULL
|| BN_is_zero(group
->field
)
356 || BN_is_negative(group
->field
)) {
357 ECerr(EC_F_EC_GROUP_SET_GENERATOR
, EC_R_INVALID_FIELD
);
362 * - require order >= 1
363 * - enforce upper bound due to Hasse thm: order can be no more than one bit
364 * longer than field cardinality
366 if (order
== NULL
|| BN_is_zero(order
) || BN_is_negative(order
)
367 || BN_num_bits(order
) > BN_num_bits(group
->field
) + 1) {
368 ECerr(EC_F_EC_GROUP_SET_GENERATOR
, EC_R_INVALID_GROUP_ORDER
);
373 * Unfortunately the cofactor is an optional field in many standards.
374 * Internally, the lib uses 0 cofactor as a marker for "unknown cofactor".
375 * So accept cofactor == NULL or cofactor >= 0.
377 if (cofactor
!= NULL
&& BN_is_negative(cofactor
)) {
378 ECerr(EC_F_EC_GROUP_SET_GENERATOR
, EC_R_UNKNOWN_COFACTOR
);
382 if (group
->generator
== NULL
) {
383 group
->generator
= EC_POINT_new(group
);
384 if (group
->generator
== NULL
)
387 if (!EC_POINT_copy(group
->generator
, generator
))
390 if (!BN_copy(group
->order
, order
))
393 /* Either take the provided positive cofactor, or try to compute it */
394 if (cofactor
!= NULL
&& !BN_is_zero(cofactor
)) {
395 if (!BN_copy(group
->cofactor
, cofactor
))
397 } else if (!ec_guess_cofactor(group
)) {
398 BN_zero(group
->cofactor
);
403 * Some groups have an order with
404 * factors of two, which makes the Montgomery setup fail.
405 * |group->mont_data| will be NULL in this case.
407 if (BN_is_odd(group
->order
)) {
408 return ec_precompute_mont_data(group
);
411 BN_MONT_CTX_free(group
->mont_data
);
412 group
->mont_data
= NULL
;
416 const EC_POINT
*EC_GROUP_get0_generator(const EC_GROUP
*group
)
418 return group
->generator
;
421 BN_MONT_CTX
*EC_GROUP_get_mont_data(const EC_GROUP
*group
)
423 return group
->mont_data
;
426 int EC_GROUP_get_order(const EC_GROUP
*group
, BIGNUM
*order
, BN_CTX
*ctx
)
428 if (group
->order
== NULL
)
430 if (!BN_copy(order
, group
->order
))
433 return !BN_is_zero(order
);
436 const BIGNUM
*EC_GROUP_get0_order(const EC_GROUP
*group
)
441 int EC_GROUP_order_bits(const EC_GROUP
*group
)
443 return group
->meth
->group_order_bits(group
);
446 int EC_GROUP_get_cofactor(const EC_GROUP
*group
, BIGNUM
*cofactor
,
450 if (group
->cofactor
== NULL
)
452 if (!BN_copy(cofactor
, group
->cofactor
))
455 return !BN_is_zero(group
->cofactor
);
458 const BIGNUM
*EC_GROUP_get0_cofactor(const EC_GROUP
*group
)
460 return group
->cofactor
;
463 void EC_GROUP_set_curve_name(EC_GROUP
*group
, int nid
)
465 group
->curve_name
= nid
;
468 int EC_GROUP_get_curve_name(const EC_GROUP
*group
)
470 return group
->curve_name
;
473 const BIGNUM
*EC_GROUP_get0_field(const EC_GROUP
*group
)
478 void EC_GROUP_set_asn1_flag(EC_GROUP
*group
, int flag
)
480 group
->asn1_flag
= flag
;
483 int EC_GROUP_get_asn1_flag(const EC_GROUP
*group
)
485 return group
->asn1_flag
;
488 void EC_GROUP_set_point_conversion_form(EC_GROUP
*group
,
489 point_conversion_form_t form
)
491 group
->asn1_form
= form
;
494 point_conversion_form_t
EC_GROUP_get_point_conversion_form(const EC_GROUP
497 return group
->asn1_form
;
500 size_t EC_GROUP_set_seed(EC_GROUP
*group
, const unsigned char *p
, size_t len
)
502 OPENSSL_free(group
->seed
);
509 if ((group
->seed
= OPENSSL_malloc(len
)) == NULL
) {
510 ECerr(EC_F_EC_GROUP_SET_SEED
, ERR_R_MALLOC_FAILURE
);
513 memcpy(group
->seed
, p
, len
);
514 group
->seed_len
= len
;
519 unsigned char *EC_GROUP_get0_seed(const EC_GROUP
*group
)
524 size_t EC_GROUP_get_seed_len(const EC_GROUP
*group
)
526 return group
->seed_len
;
529 int EC_GROUP_set_curve(EC_GROUP
*group
, const BIGNUM
*p
, const BIGNUM
*a
,
530 const BIGNUM
*b
, BN_CTX
*ctx
)
532 if (group
->meth
->group_set_curve
== 0) {
533 ECerr(EC_F_EC_GROUP_SET_CURVE
, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
536 return group
->meth
->group_set_curve(group
, p
, a
, b
, ctx
);
539 int EC_GROUP_get_curve(const EC_GROUP
*group
, BIGNUM
*p
, BIGNUM
*a
, BIGNUM
*b
,
542 if (group
->meth
->group_get_curve
== NULL
) {
543 ECerr(EC_F_EC_GROUP_GET_CURVE
, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
546 return group
->meth
->group_get_curve(group
, p
, a
, b
, ctx
);
549 #ifndef OPENSSL_NO_DEPRECATED_3_0
550 int EC_GROUP_set_curve_GFp(EC_GROUP
*group
, const BIGNUM
*p
, const BIGNUM
*a
,
551 const BIGNUM
*b
, BN_CTX
*ctx
)
553 return EC_GROUP_set_curve(group
, p
, a
, b
, ctx
);
556 int EC_GROUP_get_curve_GFp(const EC_GROUP
*group
, BIGNUM
*p
, BIGNUM
*a
,
557 BIGNUM
*b
, BN_CTX
*ctx
)
559 return EC_GROUP_get_curve(group
, p
, a
, b
, ctx
);
562 # ifndef OPENSSL_NO_EC2M
563 int EC_GROUP_set_curve_GF2m(EC_GROUP
*group
, const BIGNUM
*p
, const BIGNUM
*a
,
564 const BIGNUM
*b
, BN_CTX
*ctx
)
566 return EC_GROUP_set_curve(group
, p
, a
, b
, ctx
);
569 int EC_GROUP_get_curve_GF2m(const EC_GROUP
*group
, BIGNUM
*p
, BIGNUM
*a
,
570 BIGNUM
*b
, BN_CTX
*ctx
)
572 return EC_GROUP_get_curve(group
, p
, a
, b
, ctx
);
577 int EC_GROUP_get_degree(const EC_GROUP
*group
)
579 if (group
->meth
->group_get_degree
== 0) {
580 ECerr(EC_F_EC_GROUP_GET_DEGREE
, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
583 return group
->meth
->group_get_degree(group
);
586 int EC_GROUP_check_discriminant(const EC_GROUP
*group
, BN_CTX
*ctx
)
588 if (group
->meth
->group_check_discriminant
== 0) {
589 ECerr(EC_F_EC_GROUP_CHECK_DISCRIMINANT
,
590 ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
593 return group
->meth
->group_check_discriminant(group
, ctx
);
596 int EC_GROUP_cmp(const EC_GROUP
*a
, const EC_GROUP
*b
, BN_CTX
*ctx
)
599 BIGNUM
*a1
, *a2
, *a3
, *b1
, *b2
, *b3
;
601 BN_CTX
*ctx_new
= NULL
;
604 /* compare the field types */
605 if (EC_METHOD_get_field_type(EC_GROUP_method_of(a
)) !=
606 EC_METHOD_get_field_type(EC_GROUP_method_of(b
)))
608 /* compare the curve name (if present in both) */
609 if (EC_GROUP_get_curve_name(a
) && EC_GROUP_get_curve_name(b
) &&
610 EC_GROUP_get_curve_name(a
) != EC_GROUP_get_curve_name(b
))
612 if (a
->meth
->flags
& EC_FLAGS_CUSTOM_CURVE
)
617 ctx_new
= ctx
= BN_CTX_new();
623 a1
= BN_CTX_get(ctx
);
624 a2
= BN_CTX_get(ctx
);
625 a3
= BN_CTX_get(ctx
);
626 b1
= BN_CTX_get(ctx
);
627 b2
= BN_CTX_get(ctx
);
628 b3
= BN_CTX_get(ctx
);
632 BN_CTX_free(ctx_new
);
638 * XXX This approach assumes that the external representation of curves
639 * over the same field type is the same.
641 if (!a
->meth
->group_get_curve(a
, a1
, a2
, a3
, ctx
) ||
642 !b
->meth
->group_get_curve(b
, b1
, b2
, b3
, ctx
))
645 /* return 1 if the curve parameters are different */
646 if (r
|| BN_cmp(a1
, b1
) != 0 || BN_cmp(a2
, b2
) != 0 || BN_cmp(a3
, b3
) != 0)
649 /* XXX EC_POINT_cmp() assumes that the methods are equal */
650 /* return 1 if the generators are different */
651 if (r
|| EC_POINT_cmp(a
, EC_GROUP_get0_generator(a
),
652 EC_GROUP_get0_generator(b
), ctx
) != 0)
656 const BIGNUM
*ao
, *bo
, *ac
, *bc
;
657 /* compare the orders */
658 ao
= EC_GROUP_get0_order(a
);
659 bo
= EC_GROUP_get0_order(b
);
660 if (ao
== NULL
|| bo
== NULL
) {
661 /* return an error if either order is NULL */
665 if (BN_cmp(ao
, bo
) != 0) {
666 /* return 1 if orders are different */
671 * It gets here if the curve parameters and generator matched.
672 * Now check the optional cofactors (if both are present).
674 ac
= EC_GROUP_get0_cofactor(a
);
675 bc
= EC_GROUP_get0_cofactor(b
);
676 /* Returns 1 (mismatch) if both cofactors are specified and different */
677 if (!BN_is_zero(ac
) && !BN_is_zero(bc
) && BN_cmp(ac
, bc
) != 0)
679 /* Returns 0 if the parameters matched */
684 BN_CTX_free(ctx_new
);
689 /* functions for EC_POINT objects */
691 EC_POINT
*EC_POINT_new(const EC_GROUP
*group
)
696 ECerr(EC_F_EC_POINT_NEW
, ERR_R_PASSED_NULL_PARAMETER
);
699 if (group
->meth
->point_init
== NULL
) {
700 ECerr(EC_F_EC_POINT_NEW
, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
704 ret
= OPENSSL_zalloc(sizeof(*ret
));
706 ECerr(EC_F_EC_POINT_NEW
, ERR_R_MALLOC_FAILURE
);
710 ret
->meth
= group
->meth
;
711 ret
->curve_name
= group
->curve_name
;
713 if (!ret
->meth
->point_init(ret
)) {
721 void EC_POINT_free(EC_POINT
*point
)
726 if (point
->meth
->point_finish
!= 0)
727 point
->meth
->point_finish(point
);
731 void EC_POINT_clear_free(EC_POINT
*point
)
736 if (point
->meth
->point_clear_finish
!= 0)
737 point
->meth
->point_clear_finish(point
);
738 else if (point
->meth
->point_finish
!= 0)
739 point
->meth
->point_finish(point
);
740 OPENSSL_clear_free(point
, sizeof(*point
));
743 int EC_POINT_copy(EC_POINT
*dest
, const EC_POINT
*src
)
745 if (dest
->meth
->point_copy
== 0) {
746 ECerr(EC_F_EC_POINT_COPY
, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
749 if (dest
->meth
!= src
->meth
750 || (dest
->curve_name
!= src
->curve_name
751 && dest
->curve_name
!= 0
752 && src
->curve_name
!= 0)) {
753 ECerr(EC_F_EC_POINT_COPY
, EC_R_INCOMPATIBLE_OBJECTS
);
758 return dest
->meth
->point_copy(dest
, src
);
761 EC_POINT
*EC_POINT_dup(const EC_POINT
*a
, const EC_GROUP
*group
)
769 t
= EC_POINT_new(group
);
772 r
= EC_POINT_copy(t
, a
);
780 const EC_METHOD
*EC_POINT_method_of(const EC_POINT
*point
)
785 int EC_POINT_set_to_infinity(const EC_GROUP
*group
, EC_POINT
*point
)
787 if (group
->meth
->point_set_to_infinity
== 0) {
788 ECerr(EC_F_EC_POINT_SET_TO_INFINITY
,
789 ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
792 if (group
->meth
!= point
->meth
) {
793 ECerr(EC_F_EC_POINT_SET_TO_INFINITY
, EC_R_INCOMPATIBLE_OBJECTS
);
796 return group
->meth
->point_set_to_infinity(group
, point
);
799 int EC_POINT_set_Jprojective_coordinates_GFp(const EC_GROUP
*group
,
800 EC_POINT
*point
, const BIGNUM
*x
,
801 const BIGNUM
*y
, const BIGNUM
*z
,
804 if (group
->meth
->point_set_Jprojective_coordinates_GFp
== 0) {
805 ECerr(EC_F_EC_POINT_SET_JPROJECTIVE_COORDINATES_GFP
,
806 ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
809 if (!ec_point_is_compat(point
, group
)) {
810 ECerr(EC_F_EC_POINT_SET_JPROJECTIVE_COORDINATES_GFP
,
811 EC_R_INCOMPATIBLE_OBJECTS
);
814 return group
->meth
->point_set_Jprojective_coordinates_GFp(group
, point
, x
,
818 int EC_POINT_get_Jprojective_coordinates_GFp(const EC_GROUP
*group
,
819 const EC_POINT
*point
, BIGNUM
*x
,
820 BIGNUM
*y
, BIGNUM
*z
,
823 if (group
->meth
->point_get_Jprojective_coordinates_GFp
== 0) {
824 ECerr(EC_F_EC_POINT_GET_JPROJECTIVE_COORDINATES_GFP
,
825 ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
828 if (!ec_point_is_compat(point
, group
)) {
829 ECerr(EC_F_EC_POINT_GET_JPROJECTIVE_COORDINATES_GFP
,
830 EC_R_INCOMPATIBLE_OBJECTS
);
833 return group
->meth
->point_get_Jprojective_coordinates_GFp(group
, point
, x
,
837 int EC_POINT_set_affine_coordinates(const EC_GROUP
*group
, EC_POINT
*point
,
838 const BIGNUM
*x
, const BIGNUM
*y
,
841 if (group
->meth
->point_set_affine_coordinates
== NULL
) {
842 ECerr(EC_F_EC_POINT_SET_AFFINE_COORDINATES
,
843 ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
846 if (!ec_point_is_compat(point
, group
)) {
847 ECerr(EC_F_EC_POINT_SET_AFFINE_COORDINATES
, EC_R_INCOMPATIBLE_OBJECTS
);
850 if (!group
->meth
->point_set_affine_coordinates(group
, point
, x
, y
, ctx
))
853 if (EC_POINT_is_on_curve(group
, point
, ctx
) <= 0) {
854 ECerr(EC_F_EC_POINT_SET_AFFINE_COORDINATES
, EC_R_POINT_IS_NOT_ON_CURVE
);
860 #ifndef OPENSSL_NO_DEPRECATED_3_0
861 int EC_POINT_set_affine_coordinates_GFp(const EC_GROUP
*group
,
862 EC_POINT
*point
, const BIGNUM
*x
,
863 const BIGNUM
*y
, BN_CTX
*ctx
)
865 return EC_POINT_set_affine_coordinates(group
, point
, x
, y
, ctx
);
868 # ifndef OPENSSL_NO_EC2M
869 int EC_POINT_set_affine_coordinates_GF2m(const EC_GROUP
*group
,
870 EC_POINT
*point
, const BIGNUM
*x
,
871 const BIGNUM
*y
, BN_CTX
*ctx
)
873 return EC_POINT_set_affine_coordinates(group
, point
, x
, y
, ctx
);
878 int EC_POINT_get_affine_coordinates(const EC_GROUP
*group
,
879 const EC_POINT
*point
, BIGNUM
*x
, BIGNUM
*y
,
882 if (group
->meth
->point_get_affine_coordinates
== NULL
) {
883 ECerr(EC_F_EC_POINT_GET_AFFINE_COORDINATES
,
884 ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
887 if (!ec_point_is_compat(point
, group
)) {
888 ECerr(EC_F_EC_POINT_GET_AFFINE_COORDINATES
, EC_R_INCOMPATIBLE_OBJECTS
);
891 if (EC_POINT_is_at_infinity(group
, point
)) {
892 ECerr(EC_F_EC_POINT_GET_AFFINE_COORDINATES
, EC_R_POINT_AT_INFINITY
);
895 return group
->meth
->point_get_affine_coordinates(group
, point
, x
, y
, ctx
);
898 #ifndef OPENSSL_NO_DEPRECATED_3_0
899 int EC_POINT_get_affine_coordinates_GFp(const EC_GROUP
*group
,
900 const EC_POINT
*point
, BIGNUM
*x
,
901 BIGNUM
*y
, BN_CTX
*ctx
)
903 return EC_POINT_get_affine_coordinates(group
, point
, x
, y
, ctx
);
906 # ifndef OPENSSL_NO_EC2M
907 int EC_POINT_get_affine_coordinates_GF2m(const EC_GROUP
*group
,
908 const EC_POINT
*point
, BIGNUM
*x
,
909 BIGNUM
*y
, BN_CTX
*ctx
)
911 return EC_POINT_get_affine_coordinates(group
, point
, x
, y
, ctx
);
916 int EC_POINT_add(const EC_GROUP
*group
, EC_POINT
*r
, const EC_POINT
*a
,
917 const EC_POINT
*b
, BN_CTX
*ctx
)
919 if (group
->meth
->add
== 0) {
920 ECerr(EC_F_EC_POINT_ADD
, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
923 if (!ec_point_is_compat(r
, group
) || !ec_point_is_compat(a
, group
)
924 || !ec_point_is_compat(b
, group
)) {
925 ECerr(EC_F_EC_POINT_ADD
, EC_R_INCOMPATIBLE_OBJECTS
);
928 return group
->meth
->add(group
, r
, a
, b
, ctx
);
931 int EC_POINT_dbl(const EC_GROUP
*group
, EC_POINT
*r
, const EC_POINT
*a
,
934 if (group
->meth
->dbl
== 0) {
935 ECerr(EC_F_EC_POINT_DBL
, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
938 if (!ec_point_is_compat(r
, group
) || !ec_point_is_compat(a
, group
)) {
939 ECerr(EC_F_EC_POINT_DBL
, EC_R_INCOMPATIBLE_OBJECTS
);
942 return group
->meth
->dbl(group
, r
, a
, ctx
);
945 int EC_POINT_invert(const EC_GROUP
*group
, EC_POINT
*a
, BN_CTX
*ctx
)
947 if (group
->meth
->invert
== 0) {
948 ECerr(EC_F_EC_POINT_INVERT
, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
951 if (!ec_point_is_compat(a
, group
)) {
952 ECerr(EC_F_EC_POINT_INVERT
, EC_R_INCOMPATIBLE_OBJECTS
);
955 return group
->meth
->invert(group
, a
, ctx
);
958 int EC_POINT_is_at_infinity(const EC_GROUP
*group
, const EC_POINT
*point
)
960 if (group
->meth
->is_at_infinity
== 0) {
961 ECerr(EC_F_EC_POINT_IS_AT_INFINITY
,
962 ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
965 if (!ec_point_is_compat(point
, group
)) {
966 ECerr(EC_F_EC_POINT_IS_AT_INFINITY
, EC_R_INCOMPATIBLE_OBJECTS
);
969 return group
->meth
->is_at_infinity(group
, point
);
973 * Check whether an EC_POINT is on the curve or not. Note that the return
974 * value for this function should NOT be treated as a boolean. Return values:
975 * 1: The point is on the curve
976 * 0: The point is not on the curve
977 * -1: An error occurred
979 int EC_POINT_is_on_curve(const EC_GROUP
*group
, const EC_POINT
*point
,
982 if (group
->meth
->is_on_curve
== 0) {
983 ECerr(EC_F_EC_POINT_IS_ON_CURVE
, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
986 if (!ec_point_is_compat(point
, group
)) {
987 ECerr(EC_F_EC_POINT_IS_ON_CURVE
, EC_R_INCOMPATIBLE_OBJECTS
);
990 return group
->meth
->is_on_curve(group
, point
, ctx
);
993 int EC_POINT_cmp(const EC_GROUP
*group
, const EC_POINT
*a
, const EC_POINT
*b
,
996 if (group
->meth
->point_cmp
== 0) {
997 ECerr(EC_F_EC_POINT_CMP
, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
1000 if (!ec_point_is_compat(a
, group
) || !ec_point_is_compat(b
, group
)) {
1001 ECerr(EC_F_EC_POINT_CMP
, EC_R_INCOMPATIBLE_OBJECTS
);
1004 return group
->meth
->point_cmp(group
, a
, b
, ctx
);
1007 int EC_POINT_make_affine(const EC_GROUP
*group
, EC_POINT
*point
, BN_CTX
*ctx
)
1009 if (group
->meth
->make_affine
== 0) {
1010 ECerr(EC_F_EC_POINT_MAKE_AFFINE
, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
1013 if (!ec_point_is_compat(point
, group
)) {
1014 ECerr(EC_F_EC_POINT_MAKE_AFFINE
, EC_R_INCOMPATIBLE_OBJECTS
);
1017 return group
->meth
->make_affine(group
, point
, ctx
);
1020 int EC_POINTs_make_affine(const EC_GROUP
*group
, size_t num
,
1021 EC_POINT
*points
[], BN_CTX
*ctx
)
1025 if (group
->meth
->points_make_affine
== 0) {
1026 ECerr(EC_F_EC_POINTS_MAKE_AFFINE
, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED
);
1029 for (i
= 0; i
< num
; i
++) {
1030 if (!ec_point_is_compat(points
[i
], group
)) {
1031 ECerr(EC_F_EC_POINTS_MAKE_AFFINE
, EC_R_INCOMPATIBLE_OBJECTS
);
1035 return group
->meth
->points_make_affine(group
, num
, points
, ctx
);
1039 * Functions for point multiplication. If group->meth->mul is 0, we use the
1040 * wNAF-based implementations in ec_mult.c; otherwise we dispatch through
1044 int EC_POINTs_mul(const EC_GROUP
*group
, EC_POINT
*r
, const BIGNUM
*scalar
,
1045 size_t num
, const EC_POINT
*points
[],
1046 const BIGNUM
*scalars
[], BN_CTX
*ctx
)
1051 BN_CTX
*new_ctx
= NULL
;
1054 if ((scalar
== NULL
) && (num
== 0)) {
1055 return EC_POINT_set_to_infinity(group
, r
);
1058 if (!ec_point_is_compat(r
, group
)) {
1059 ECerr(EC_F_EC_POINTS_MUL
, EC_R_INCOMPATIBLE_OBJECTS
);
1062 for (i
= 0; i
< num
; i
++) {
1063 if (!ec_point_is_compat(points
[i
], group
)) {
1064 ECerr(EC_F_EC_POINTS_MUL
, EC_R_INCOMPATIBLE_OBJECTS
);
1071 ctx
= new_ctx
= BN_CTX_secure_new();
1074 ECerr(EC_F_EC_POINTS_MUL
, ERR_R_INTERNAL_ERROR
);
1078 if (group
->meth
->mul
!= NULL
)
1079 ret
= group
->meth
->mul(group
, r
, scalar
, num
, points
, scalars
, ctx
);
1082 ret
= ec_wNAF_mul(group
, r
, scalar
, num
, points
, scalars
, ctx
);
1085 BN_CTX_free(new_ctx
);
1090 int EC_POINT_mul(const EC_GROUP
*group
, EC_POINT
*r
, const BIGNUM
*g_scalar
,
1091 const EC_POINT
*point
, const BIGNUM
*p_scalar
, BN_CTX
*ctx
)
1093 /* just a convenient interface to EC_POINTs_mul() */
1095 const EC_POINT
*points
[1];
1096 const BIGNUM
*scalars
[1];
1099 scalars
[0] = p_scalar
;
1101 return EC_POINTs_mul(group
, r
, g_scalar
,
1103 && p_scalar
!= NULL
), points
, scalars
, ctx
);
1106 int EC_GROUP_precompute_mult(EC_GROUP
*group
, BN_CTX
*ctx
)
1108 if (group
->meth
->mul
== 0)
1110 return ec_wNAF_precompute_mult(group
, ctx
);
1112 if (group
->meth
->precompute_mult
!= 0)
1113 return group
->meth
->precompute_mult(group
, ctx
);
1115 return 1; /* nothing to do, so report success */
1118 int EC_GROUP_have_precompute_mult(const EC_GROUP
*group
)
1120 if (group
->meth
->mul
== 0)
1122 return ec_wNAF_have_precompute_mult(group
);
1124 if (group
->meth
->have_precompute_mult
!= 0)
1125 return group
->meth
->have_precompute_mult(group
);
1127 return 0; /* cannot tell whether precomputation has
1132 * ec_precompute_mont_data sets |group->mont_data| from |group->order| and
1133 * returns one on success. On error it returns zero.
1135 static int ec_precompute_mont_data(EC_GROUP
*group
)
1137 BN_CTX
*ctx
= BN_CTX_new_ex(group
->libctx
);
1140 BN_MONT_CTX_free(group
->mont_data
);
1141 group
->mont_data
= NULL
;
1146 group
->mont_data
= BN_MONT_CTX_new();
1147 if (group
->mont_data
== NULL
)
1150 if (!BN_MONT_CTX_set(group
->mont_data
, group
->order
, ctx
)) {
1151 BN_MONT_CTX_free(group
->mont_data
);
1152 group
->mont_data
= NULL
;
1165 int EC_KEY_set_ex_data(EC_KEY
*key
, int idx
, void *arg
)
1167 return CRYPTO_set_ex_data(&key
->ex_data
, idx
, arg
);
1170 void *EC_KEY_get_ex_data(const EC_KEY
*key
, int idx
)
1172 return CRYPTO_get_ex_data(&key
->ex_data
, idx
);
1176 int ec_group_simple_order_bits(const EC_GROUP
*group
)
1178 if (group
->order
== NULL
)
1180 return BN_num_bits(group
->order
);
1183 static int ec_field_inverse_mod_ord(const EC_GROUP
*group
, BIGNUM
*r
,
1184 const BIGNUM
*x
, BN_CTX
*ctx
)
1189 BN_CTX
*new_ctx
= NULL
;
1192 if (group
->mont_data
== NULL
)
1197 ctx
= new_ctx
= BN_CTX_secure_new();
1203 if ((e
= BN_CTX_get(ctx
)) == NULL
)
1207 * We want inverse in constant time, therefore we utilize the fact
1208 * order must be prime and use Fermats Little Theorem instead.
1210 if (!BN_set_word(e
, 2))
1212 if (!BN_sub(e
, group
->order
, e
))
1215 * Exponent e is public.
1216 * No need for scatter-gather or BN_FLG_CONSTTIME.
1218 if (!BN_mod_exp_mont(r
, x
, e
, group
->order
, ctx
, group
->mont_data
))
1226 BN_CTX_free(new_ctx
);
1232 * Default behavior, if group->meth->field_inverse_mod_ord is NULL:
1233 * - When group->order is even, this function returns an error.
1234 * - When group->order is otherwise composite, the correctness
1235 * of the output is not guaranteed.
1236 * - When x is outside the range [1, group->order), the correctness
1237 * of the output is not guaranteed.
1238 * - Otherwise, this function returns the multiplicative inverse in the
1239 * range [1, group->order).
1241 * EC_METHODs must implement their own field_inverse_mod_ord for
1242 * other functionality.
1244 int ec_group_do_inverse_ord(const EC_GROUP
*group
, BIGNUM
*res
,
1245 const BIGNUM
*x
, BN_CTX
*ctx
)
1247 if (group
->meth
->field_inverse_mod_ord
!= NULL
)
1248 return group
->meth
->field_inverse_mod_ord(group
, res
, x
, ctx
);
1250 return ec_field_inverse_mod_ord(group
, res
, x
, ctx
);
1254 * Coordinate blinding for EC_POINT.
1256 * The underlying EC_METHOD can optionally implement this function:
1257 * underlying implementations should return 0 on errors, or 1 on
1260 * This wrapper returns 1 in case the underlying EC_METHOD does not
1261 * support coordinate blinding.
1263 int ec_point_blind_coordinates(const EC_GROUP
*group
, EC_POINT
*p
, BN_CTX
*ctx
)
1265 if (group
->meth
->blind_coordinates
== NULL
)
1266 return 1; /* ignore if not implemented */
1268 return group
->meth
->blind_coordinates(group
, p
, ctx
);