TEST: Add test to exercise OPENSSL_CTX_set0_default()
[openssl.git] / test / ectest.c
1 /*
2  * Copyright 2001-2020 The OpenSSL Project Authors. All Rights Reserved.
3  * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved
4  *
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
9  */
10
11 /*
12  * We need access to the deprecated EC_POINTs_mul, EC_GROUP_precompute_mult,
13  * and EC_GROUP_have_precompute_mult for testing purposes
14  * when the deprecated calls are not hidden
15  */
16 #ifndef OPENSSL_NO_DEPRECATED_3_0
17 # define OPENSSL_SUPPRESS_DEPRECATED
18 #endif
19
20 #include <string.h>
21 #include "internal/nelem.h"
22 #include "testutil.h"
23
24 #ifndef OPENSSL_NO_EC
25 # include <openssl/ec.h>
26 # ifndef OPENSSL_NO_ENGINE
27 #  include <openssl/engine.h>
28 # endif
29 # include <openssl/err.h>
30 # include <openssl/obj_mac.h>
31 # include <openssl/objects.h>
32 # include <openssl/rand.h>
33 # include <openssl/bn.h>
34 # include <openssl/opensslconf.h>
35
36 static size_t crv_len = 0;
37 static EC_builtin_curve *curves = NULL;
38
39 /* test multiplication with group order, long and negative scalars */
40 static int group_order_tests(EC_GROUP *group)
41 {
42     BIGNUM *n1 = NULL, *n2 = NULL, *order = NULL;
43     EC_POINT *P = NULL, *Q = NULL, *R = NULL, *S = NULL;
44     const EC_POINT *G = NULL;
45     BN_CTX *ctx = NULL;
46     int i = 0, r = 0;
47
48     if (!TEST_ptr(n1 = BN_new())
49         || !TEST_ptr(n2 = BN_new())
50         || !TEST_ptr(order = BN_new())
51         || !TEST_ptr(ctx = BN_CTX_new())
52         || !TEST_ptr(G = EC_GROUP_get0_generator(group))
53         || !TEST_ptr(P = EC_POINT_new(group))
54         || !TEST_ptr(Q = EC_POINT_new(group))
55         || !TEST_ptr(R = EC_POINT_new(group))
56         || !TEST_ptr(S = EC_POINT_new(group)))
57         goto err;
58
59     if (!TEST_true(EC_GROUP_get_order(group, order, ctx))
60         || !TEST_true(EC_POINT_mul(group, Q, order, NULL, NULL, ctx))
61         || !TEST_true(EC_POINT_is_at_infinity(group, Q))
62 # ifndef OPENSSL_NO_DEPRECATED_3_0
63         || !TEST_true(EC_GROUP_precompute_mult(group, ctx))
64 # endif
65         || !TEST_true(EC_POINT_mul(group, Q, order, NULL, NULL, ctx))
66         || !TEST_true(EC_POINT_is_at_infinity(group, Q))
67         || !TEST_true(EC_POINT_copy(P, G))
68         || !TEST_true(BN_one(n1))
69         || !TEST_true(EC_POINT_mul(group, Q, n1, NULL, NULL, ctx))
70         || !TEST_int_eq(0, EC_POINT_cmp(group, Q, P, ctx))
71         || !TEST_true(BN_sub(n1, order, n1))
72         || !TEST_true(EC_POINT_mul(group, Q, n1, NULL, NULL, ctx))
73         || !TEST_true(EC_POINT_invert(group, Q, ctx))
74         || !TEST_int_eq(0, EC_POINT_cmp(group, Q, P, ctx)))
75         goto err;
76
77     for (i = 1; i <= 2; i++) {
78 # ifndef OPENSSL_NO_DEPRECATED_3_0
79         const BIGNUM *scalars[6];
80         const EC_POINT *points[6];
81 # endif
82
83         if (!TEST_true(BN_set_word(n1, i))
84             /*
85              * If i == 1, P will be the predefined generator for which
86              * EC_GROUP_precompute_mult has set up precomputation.
87              */
88             || !TEST_true(EC_POINT_mul(group, P, n1, NULL, NULL, ctx))
89             || (i == 1 && !TEST_int_eq(0, EC_POINT_cmp(group, P, G, ctx)))
90             || !TEST_true(BN_one(n1))
91             /* n1 = 1 - order */
92             || !TEST_true(BN_sub(n1, n1, order))
93             || !TEST_true(EC_POINT_mul(group, Q, NULL, P, n1, ctx))
94             || !TEST_int_eq(0, EC_POINT_cmp(group, Q, P, ctx))
95
96             /* n2 = 1 + order */
97             || !TEST_true(BN_add(n2, order, BN_value_one()))
98             || !TEST_true(EC_POINT_mul(group, Q, NULL, P, n2, ctx))
99             || !TEST_int_eq(0, EC_POINT_cmp(group, Q, P, ctx))
100
101             /* n2 = (1 - order) * (1 + order) = 1 - order^2 */
102             || !TEST_true(BN_mul(n2, n1, n2, ctx))
103             || !TEST_true(EC_POINT_mul(group, Q, NULL, P, n2, ctx))
104             || !TEST_int_eq(0, EC_POINT_cmp(group, Q, P, ctx)))
105             goto err;
106
107         /* n2 = order^2 - 1 */
108         BN_set_negative(n2, 0);
109         if (!TEST_true(EC_POINT_mul(group, Q, NULL, P, n2, ctx))
110             /* Add P to verify the result. */
111             || !TEST_true(EC_POINT_add(group, Q, Q, P, ctx))
112             || !TEST_true(EC_POINT_is_at_infinity(group, Q))
113             || !TEST_false(EC_POINT_is_at_infinity(group, P)))
114             goto err;
115
116 # ifndef OPENSSL_NO_DEPRECATED_3_0
117         /* Exercise EC_POINTs_mul, including corner cases. */
118         scalars[0] = scalars[1] = BN_value_one();
119         points[0]  = points[1]  = P;
120
121         if (!TEST_true(EC_POINTs_mul(group, R, NULL, 2, points, scalars, ctx))
122             || !TEST_true(EC_POINT_dbl(group, S, points[0], ctx))
123             || !TEST_int_eq(0, EC_POINT_cmp(group, R, S, ctx)))
124             goto err;
125
126         scalars[0] = n1;
127         points[0] = Q;          /* => infinity */
128         scalars[1] = n2;
129         points[1] = P;          /* => -P */
130         scalars[2] = n1;
131         points[2] = Q;          /* => infinity */
132         scalars[3] = n2;
133         points[3] = Q;          /* => infinity */
134         scalars[4] = n1;
135         points[4] = P;          /* => P */
136         scalars[5] = n2;
137         points[5] = Q;          /* => infinity */
138         if (!TEST_true(EC_POINTs_mul(group, P, NULL, 6, points, scalars, ctx))
139             || !TEST_true(EC_POINT_is_at_infinity(group, P)))
140             goto err;
141 # endif
142     }
143
144     r = 1;
145 err:
146     if (r == 0 && i != 0)
147         TEST_info(i == 1 ? "allowing precomputation" :
148                            "without precomputation");
149     EC_POINT_free(P);
150     EC_POINT_free(Q);
151     EC_POINT_free(R);
152     EC_POINT_free(S);
153     BN_free(n1);
154     BN_free(n2);
155     BN_free(order);
156     BN_CTX_free(ctx);
157     return r;
158 }
159
160 static int prime_field_tests(void)
161 {
162     BN_CTX *ctx = NULL;
163     BIGNUM *p = NULL, *a = NULL, *b = NULL, *scalar3 = NULL;
164     EC_GROUP *group = NULL;
165     EC_POINT *P = NULL, *Q = NULL, *R = NULL;
166     BIGNUM *x = NULL, *y = NULL, *z = NULL, *yplusone = NULL;
167 # ifndef OPENSSL_NO_DEPRECATED_3_0
168     const EC_POINT *points[4];
169     const BIGNUM *scalars[4];
170 # endif
171     unsigned char buf[100];
172     size_t len, r = 0;
173     int k;
174
175     if (!TEST_ptr(ctx = BN_CTX_new())
176         || !TEST_ptr(p = BN_new())
177         || !TEST_ptr(a = BN_new())
178         || !TEST_ptr(b = BN_new())
179         || !TEST_true(BN_hex2bn(&p, "17"))
180         || !TEST_true(BN_hex2bn(&a, "1"))
181         || !TEST_true(BN_hex2bn(&b, "1"))
182         || !TEST_ptr(group = EC_GROUP_new_curve_GFp(p, a, b, ctx))
183         || !TEST_true(EC_GROUP_get_curve(group, p, a, b, ctx)))
184         goto err;
185
186     TEST_info("Curve defined by Weierstrass equation");
187     TEST_note("     y^2 = x^3 + a*x + b (mod p)");
188     test_output_bignum("a", a);
189     test_output_bignum("b", b);
190     test_output_bignum("p", p);
191
192     buf[0] = 0;
193     if (!TEST_ptr(P = EC_POINT_new(group))
194         || !TEST_ptr(Q = EC_POINT_new(group))
195         || !TEST_ptr(R = EC_POINT_new(group))
196         || !TEST_true(EC_POINT_set_to_infinity(group, P))
197         || !TEST_true(EC_POINT_is_at_infinity(group, P))
198         || !TEST_true(EC_POINT_oct2point(group, Q, buf, 1, ctx))
199         || !TEST_true(EC_POINT_add(group, P, P, Q, ctx))
200         || !TEST_true(EC_POINT_is_at_infinity(group, P))
201         || !TEST_ptr(x = BN_new())
202         || !TEST_ptr(y = BN_new())
203         || !TEST_ptr(z = BN_new())
204         || !TEST_ptr(yplusone = BN_new())
205         || !TEST_true(BN_hex2bn(&x, "D"))
206         || !TEST_true(EC_POINT_set_compressed_coordinates(group, Q, x, 1, ctx)))
207         goto err;
208
209     if (!TEST_int_gt(EC_POINT_is_on_curve(group, Q, ctx), 0)) {
210         if (!TEST_true(EC_POINT_get_affine_coordinates(group, Q, x, y, ctx)))
211             goto err;
212         TEST_info("Point is not on curve");
213         test_output_bignum("x", x);
214         test_output_bignum("y", y);
215         goto err;
216     }
217
218     TEST_note("A cyclic subgroup:");
219     k = 100;
220     do {
221         if (!TEST_int_ne(k--, 0))
222             goto err;
223
224         if (EC_POINT_is_at_infinity(group, P)) {
225             TEST_note("     point at infinity");
226         } else {
227             if (!TEST_true(EC_POINT_get_affine_coordinates(group, P, x, y,
228                                                            ctx)))
229                 goto err;
230
231             test_output_bignum("x", x);
232             test_output_bignum("y", y);
233         }
234
235         if (!TEST_true(EC_POINT_copy(R, P))
236             || !TEST_true(EC_POINT_add(group, P, P, Q, ctx)))
237             goto err;
238
239     } while (!EC_POINT_is_at_infinity(group, P));
240
241     if (!TEST_true(EC_POINT_add(group, P, Q, R, ctx))
242         || !TEST_true(EC_POINT_is_at_infinity(group, P)))
243         goto err;
244
245     len =
246         EC_POINT_point2oct(group, Q, POINT_CONVERSION_COMPRESSED, buf,
247                            sizeof(buf), ctx);
248     if (!TEST_size_t_ne(len, 0)
249         || !TEST_true(EC_POINT_oct2point(group, P, buf, len, ctx))
250         || !TEST_int_eq(0, EC_POINT_cmp(group, P, Q, ctx)))
251         goto err;
252     test_output_memory("Generator as octet string, compressed form:",
253                        buf, len);
254
255     len = EC_POINT_point2oct(group, Q, POINT_CONVERSION_UNCOMPRESSED,
256                              buf, sizeof(buf), ctx);
257     if (!TEST_size_t_ne(len, 0)
258         || !TEST_true(EC_POINT_oct2point(group, P, buf, len, ctx))
259         || !TEST_int_eq(0, EC_POINT_cmp(group, P, Q, ctx)))
260         goto err;
261     test_output_memory("Generator as octet string, uncompressed form:",
262                        buf, len);
263
264     len = EC_POINT_point2oct(group, Q, POINT_CONVERSION_HYBRID,
265                              buf, sizeof(buf), ctx);
266     if (!TEST_size_t_ne(len, 0)
267         || !TEST_true(EC_POINT_oct2point(group, P, buf, len, ctx))
268         || !TEST_int_eq(0, EC_POINT_cmp(group, P, Q, ctx)))
269         goto err;
270     test_output_memory("Generator as octet string, hybrid form:",
271                        buf, len);
272
273     if (!TEST_true(EC_POINT_invert(group, P, ctx))
274         || !TEST_int_eq(0, EC_POINT_cmp(group, P, R, ctx))
275
276     /*
277      * Curve secp160r1 (Certicom Research SEC 2 Version 1.0, section 2.4.2,
278      * 2000) -- not a NIST curve, but commonly used
279      */
280
281         || !TEST_true(BN_hex2bn(&p,                         "FFFFFFFF"
282                                     "FFFFFFFFFFFFFFFFFFFFFFFF7FFFFFFF"))
283         || !TEST_int_eq(1, BN_check_prime(p, ctx, NULL))
284         || !TEST_true(BN_hex2bn(&a,                         "FFFFFFFF"
285                                     "FFFFFFFFFFFFFFFFFFFFFFFF7FFFFFFC"))
286         || !TEST_true(BN_hex2bn(&b,                         "1C97BEFC"
287                                     "54BD7A8B65ACF89F81D4D4ADC565FA45"))
288         || !TEST_true(EC_GROUP_set_curve(group, p, a, b, ctx))
289         || !TEST_true(BN_hex2bn(&x,                         "4A96B568"
290                                     "8EF573284664698968C38BB913CBFC82"))
291         || !TEST_true(BN_hex2bn(&y,                         "23a62855"
292                                     "3168947d59dcc912042351377ac5fb32"))
293         || !TEST_true(BN_add(yplusone, y, BN_value_one()))
294     /*
295      * When (x, y) is on the curve, (x, y + 1) is, as it happens, not,
296      * and therefore setting the coordinates should fail.
297      */
298         || !TEST_false(EC_POINT_set_affine_coordinates(group, P, x, yplusone,
299                                                        ctx))
300         || !TEST_true(EC_POINT_set_affine_coordinates(group, P, x, y, ctx))
301         || !TEST_int_gt(EC_POINT_is_on_curve(group, P, ctx), 0)
302         || !TEST_true(BN_hex2bn(&z,                       "0100000000"
303                                     "000000000001F4C8F927AED3CA752257"))
304         || !TEST_true(EC_GROUP_set_generator(group, P, z, BN_value_one()))
305         || !TEST_true(EC_POINT_get_affine_coordinates(group, P, x, y, ctx)))
306         goto err;
307     TEST_info("SEC2 curve secp160r1 -- Generator");
308     test_output_bignum("x", x);
309     test_output_bignum("y", y);
310     /* G_y value taken from the standard: */
311     if (!TEST_true(BN_hex2bn(&z,                         "23a62855"
312                                  "3168947d59dcc912042351377ac5fb32"))
313         || !TEST_BN_eq(y, z)
314         || !TEST_int_eq(EC_GROUP_get_degree(group), 160)
315         || !group_order_tests(group)
316
317     /* Curve P-192 (FIPS PUB 186-2, App. 6) */
318
319         || !TEST_true(BN_hex2bn(&p,                 "FFFFFFFFFFFFFFFF"
320                                     "FFFFFFFFFFFFFFFEFFFFFFFFFFFFFFFF"))
321         || !TEST_int_eq(1, BN_check_prime(p, ctx, NULL))
322         || !TEST_true(BN_hex2bn(&a,                 "FFFFFFFFFFFFFFFF"
323                                     "FFFFFFFFFFFFFFFEFFFFFFFFFFFFFFFC"))
324         || !TEST_true(BN_hex2bn(&b,                 "64210519E59C80E7"
325                                     "0FA7E9AB72243049FEB8DEECC146B9B1"))
326         || !TEST_true(EC_GROUP_set_curve(group, p, a, b, ctx))
327         || !TEST_true(BN_hex2bn(&x,                 "188DA80EB03090F6"
328                                     "7CBF20EB43A18800F4FF0AFD82FF1012"))
329         || !TEST_true(EC_POINT_set_compressed_coordinates(group, P, x, 1, ctx))
330         || !TEST_int_gt(EC_POINT_is_on_curve(group, P, ctx), 0)
331         || !TEST_true(BN_hex2bn(&z,                 "FFFFFFFFFFFFFFFF"
332                                     "FFFFFFFF99DEF836146BC9B1B4D22831"))
333         || !TEST_true(EC_GROUP_set_generator(group, P, z, BN_value_one()))
334         || !TEST_true(EC_POINT_get_affine_coordinates(group, P, x, y, ctx)))
335         goto err;
336
337     TEST_info("NIST curve P-192 -- Generator");
338     test_output_bignum("x", x);
339     test_output_bignum("y", y);
340     /* G_y value taken from the standard: */
341     if (!TEST_true(BN_hex2bn(&z,                 "07192B95FFC8DA78"
342                                  "631011ED6B24CDD573F977A11E794811"))
343         || !TEST_BN_eq(y, z)
344         || !TEST_true(BN_add(yplusone, y, BN_value_one()))
345     /*
346      * When (x, y) is on the curve, (x, y + 1) is, as it happens, not,
347      * and therefore setting the coordinates should fail.
348      */
349         || !TEST_false(EC_POINT_set_affine_coordinates(group, P, x, yplusone,
350                                                        ctx))
351         || !TEST_int_eq(EC_GROUP_get_degree(group), 192)
352         || !group_order_tests(group)
353
354     /* Curve P-224 (FIPS PUB 186-2, App. 6) */
355
356         || !TEST_true(BN_hex2bn(&p,         "FFFFFFFFFFFFFFFFFFFFFFFF"
357                                     "FFFFFFFF000000000000000000000001"))
358         || !TEST_int_eq(1, BN_check_prime(p, ctx, NULL))
359         || !TEST_true(BN_hex2bn(&a,         "FFFFFFFFFFFFFFFFFFFFFFFF"
360                                     "FFFFFFFEFFFFFFFFFFFFFFFFFFFFFFFE"))
361         || !TEST_true(BN_hex2bn(&b,         "B4050A850C04B3ABF5413256"
362                                     "5044B0B7D7BFD8BA270B39432355FFB4"))
363         || !TEST_true(EC_GROUP_set_curve(group, p, a, b, ctx))
364         || !TEST_true(BN_hex2bn(&x,         "B70E0CBD6BB4BF7F321390B9"
365                                     "4A03C1D356C21122343280D6115C1D21"))
366         || !TEST_true(EC_POINT_set_compressed_coordinates(group, P, x, 0, ctx))
367         || !TEST_int_gt(EC_POINT_is_on_curve(group, P, ctx), 0)
368         || !TEST_true(BN_hex2bn(&z,         "FFFFFFFFFFFFFFFFFFFFFFFF"
369                                     "FFFF16A2E0B8F03E13DD29455C5C2A3D"))
370         || !TEST_true(EC_GROUP_set_generator(group, P, z, BN_value_one()))
371         || !TEST_true(EC_POINT_get_affine_coordinates(group, P, x, y, ctx)))
372         goto err;
373
374     TEST_info("NIST curve P-224 -- Generator");
375     test_output_bignum("x", x);
376     test_output_bignum("y", y);
377     /* G_y value taken from the standard: */
378     if (!TEST_true(BN_hex2bn(&z,         "BD376388B5F723FB4C22DFE6"
379                                  "CD4375A05A07476444D5819985007E34"))
380         || !TEST_BN_eq(y, z)
381         || !TEST_true(BN_add(yplusone, y, BN_value_one()))
382     /*
383      * When (x, y) is on the curve, (x, y + 1) is, as it happens, not,
384      * and therefore setting the coordinates should fail.
385      */
386         || !TEST_false(EC_POINT_set_affine_coordinates(group, P, x, yplusone,
387                                                        ctx))
388         || !TEST_int_eq(EC_GROUP_get_degree(group), 224)
389         || !group_order_tests(group)
390
391     /* Curve P-256 (FIPS PUB 186-2, App. 6) */
392
393         || !TEST_true(BN_hex2bn(&p, "FFFFFFFF000000010000000000000000"
394                                     "00000000FFFFFFFFFFFFFFFFFFFFFFFF"))
395         || !TEST_int_eq(1, BN_check_prime(p, ctx, NULL))
396         || !TEST_true(BN_hex2bn(&a, "FFFFFFFF000000010000000000000000"
397                                     "00000000FFFFFFFFFFFFFFFFFFFFFFFC"))
398         || !TEST_true(BN_hex2bn(&b, "5AC635D8AA3A93E7B3EBBD55769886BC"
399                                     "651D06B0CC53B0F63BCE3C3E27D2604B"))
400         || !TEST_true(EC_GROUP_set_curve(group, p, a, b, ctx))
401
402         || !TEST_true(BN_hex2bn(&x, "6B17D1F2E12C4247F8BCE6E563A440F2"
403                                     "77037D812DEB33A0F4A13945D898C296"))
404         || !TEST_true(EC_POINT_set_compressed_coordinates(group, P, x, 1, ctx))
405         || !TEST_int_gt(EC_POINT_is_on_curve(group, P, ctx), 0)
406         || !TEST_true(BN_hex2bn(&z, "FFFFFFFF00000000FFFFFFFFFFFFFFFF"
407                                     "BCE6FAADA7179E84F3B9CAC2FC632551"))
408         || !TEST_true(EC_GROUP_set_generator(group, P, z, BN_value_one()))
409         || !TEST_true(EC_POINT_get_affine_coordinates(group, P, x, y, ctx)))
410         goto err;
411
412     TEST_info("NIST curve P-256 -- Generator");
413     test_output_bignum("x", x);
414     test_output_bignum("y", y);
415     /* G_y value taken from the standard: */
416     if (!TEST_true(BN_hex2bn(&z, "4FE342E2FE1A7F9B8EE7EB4A7C0F9E16"
417                                  "2BCE33576B315ECECBB6406837BF51F5"))
418         || !TEST_BN_eq(y, z)
419         || !TEST_true(BN_add(yplusone, y, BN_value_one()))
420     /*
421      * When (x, y) is on the curve, (x, y + 1) is, as it happens, not,
422      * and therefore setting the coordinates should fail.
423      */
424         || !TEST_false(EC_POINT_set_affine_coordinates(group, P, x, yplusone,
425                                                        ctx))
426         || !TEST_int_eq(EC_GROUP_get_degree(group), 256)
427         || !group_order_tests(group)
428
429     /* Curve P-384 (FIPS PUB 186-2, App. 6) */
430
431         || !TEST_true(BN_hex2bn(&p, "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
432                                     "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFE"
433                                     "FFFFFFFF0000000000000000FFFFFFFF"))
434         || !TEST_int_eq(1, BN_check_prime(p, ctx, NULL))
435         || !TEST_true(BN_hex2bn(&a, "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
436                                     "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFE"
437                                     "FFFFFFFF0000000000000000FFFFFFFC"))
438         || !TEST_true(BN_hex2bn(&b, "B3312FA7E23EE7E4988E056BE3F82D19"
439                                     "181D9C6EFE8141120314088F5013875A"
440                                     "C656398D8A2ED19D2A85C8EDD3EC2AEF"))
441         || !TEST_true(EC_GROUP_set_curve(group, p, a, b, ctx))
442
443         || !TEST_true(BN_hex2bn(&x, "AA87CA22BE8B05378EB1C71EF320AD74"
444                                     "6E1D3B628BA79B9859F741E082542A38"
445                                     "5502F25DBF55296C3A545E3872760AB7"))
446         || !TEST_true(EC_POINT_set_compressed_coordinates(group, P, x, 1, ctx))
447         || !TEST_int_gt(EC_POINT_is_on_curve(group, P, ctx), 0)
448         || !TEST_true(BN_hex2bn(&z, "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
449                                     "FFFFFFFFFFFFFFFFC7634D81F4372DDF"
450                                     "581A0DB248B0A77AECEC196ACCC52973"))
451         || !TEST_true(EC_GROUP_set_generator(group, P, z, BN_value_one()))
452         || !TEST_true(EC_POINT_get_affine_coordinates(group, P, x, y, ctx)))
453         goto err;
454
455     TEST_info("NIST curve P-384 -- Generator");
456     test_output_bignum("x", x);
457     test_output_bignum("y", y);
458     /* G_y value taken from the standard: */
459     if (!TEST_true(BN_hex2bn(&z, "3617DE4A96262C6F5D9E98BF9292DC29"
460                                  "F8F41DBD289A147CE9DA3113B5F0B8C0"
461                                  "0A60B1CE1D7E819D7A431D7C90EA0E5F"))
462         || !TEST_BN_eq(y, z)
463         || !TEST_true(BN_add(yplusone, y, BN_value_one()))
464     /*
465      * When (x, y) is on the curve, (x, y + 1) is, as it happens, not,
466      * and therefore setting the coordinates should fail.
467      */
468         || !TEST_false(EC_POINT_set_affine_coordinates(group, P, x, yplusone,
469                                                        ctx))
470         || !TEST_int_eq(EC_GROUP_get_degree(group), 384)
471         || !group_order_tests(group)
472
473     /* Curve P-521 (FIPS PUB 186-2, App. 6) */
474         || !TEST_true(BN_hex2bn(&p,                              "1FF"
475                                     "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
476                                     "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
477                                     "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
478                                     "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"))
479         || !TEST_int_eq(1, BN_check_prime(p, ctx, NULL))
480         || !TEST_true(BN_hex2bn(&a,                              "1FF"
481                                     "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
482                                     "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
483                                     "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
484                                     "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFC"))
485         || !TEST_true(BN_hex2bn(&b,                              "051"
486                                     "953EB9618E1C9A1F929A21A0B68540EE"
487                                     "A2DA725B99B315F3B8B489918EF109E1"
488                                     "56193951EC7E937B1652C0BD3BB1BF07"
489                                     "3573DF883D2C34F1EF451FD46B503F00"))
490         || !TEST_true(EC_GROUP_set_curve(group, p, a, b, ctx))
491         || !TEST_true(BN_hex2bn(&x,                               "C6"
492                                     "858E06B70404E9CD9E3ECB662395B442"
493                                     "9C648139053FB521F828AF606B4D3DBA"
494                                     "A14B5E77EFE75928FE1DC127A2FFA8DE"
495                                     "3348B3C1856A429BF97E7E31C2E5BD66"))
496         || !TEST_true(EC_POINT_set_compressed_coordinates(group, P, x, 0, ctx))
497         || !TEST_int_gt(EC_POINT_is_on_curve(group, P, ctx), 0)
498         || !TEST_true(BN_hex2bn(&z,                              "1FF"
499                                     "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
500                                     "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFA"
501                                     "51868783BF2F966B7FCC0148F709A5D0"
502                                     "3BB5C9B8899C47AEBB6FB71E91386409"))
503         || !TEST_true(EC_GROUP_set_generator(group, P, z, BN_value_one()))
504         || !TEST_true(EC_POINT_get_affine_coordinates(group, P, x, y, ctx)))
505         goto err;
506
507     TEST_info("NIST curve P-521 -- Generator");
508     test_output_bignum("x", x);
509     test_output_bignum("y", y);
510     /* G_y value taken from the standard: */
511     if (!TEST_true(BN_hex2bn(&z,                              "118"
512                                  "39296A789A3BC0045C8A5FB42C7D1BD9"
513                                  "98F54449579B446817AFBD17273E662C"
514                                  "97EE72995EF42640C550B9013FAD0761"
515                                  "353C7086A272C24088BE94769FD16650"))
516         || !TEST_BN_eq(y, z)
517         || !TEST_true(BN_add(yplusone, y, BN_value_one()))
518     /*
519      * When (x, y) is on the curve, (x, y + 1) is, as it happens, not,
520      * and therefore setting the coordinates should fail.
521      */
522         || !TEST_false(EC_POINT_set_affine_coordinates(group, P, x, yplusone,
523                                                        ctx))
524         || !TEST_int_eq(EC_GROUP_get_degree(group), 521)
525         || !group_order_tests(group)
526
527     /* more tests using the last curve */
528
529     /* Restore the point that got mangled in the (x, y + 1) test. */
530         || !TEST_true(EC_POINT_set_affine_coordinates(group, P, x, y, ctx))
531         || !TEST_true(EC_POINT_copy(Q, P))
532         || !TEST_false(EC_POINT_is_at_infinity(group, Q))
533         || !TEST_true(EC_POINT_dbl(group, P, P, ctx))
534         || !TEST_int_gt(EC_POINT_is_on_curve(group, P, ctx), 0)
535         || !TEST_true(EC_POINT_invert(group, Q, ctx))       /* P = -2Q */
536         || !TEST_true(EC_POINT_add(group, R, P, Q, ctx))
537         || !TEST_true(EC_POINT_add(group, R, R, Q, ctx))
538         || !TEST_true(EC_POINT_is_at_infinity(group, R))    /* R = P + 2Q */
539         || !TEST_false(EC_POINT_is_at_infinity(group, Q)))
540         goto err;
541
542 # ifndef OPENSSL_NO_DEPRECATED_3_0
543     TEST_note("combined multiplication ...");
544     points[0] = Q;
545     points[1] = Q;
546     points[2] = Q;
547     points[3] = Q;
548
549     if (!TEST_true(EC_GROUP_get_order(group, z, ctx))
550         || !TEST_true(BN_add(y, z, BN_value_one()))
551         || !TEST_BN_even(y)
552         || !TEST_true(BN_rshift1(y, y)))
553         goto err;
554
555     scalars[0] = y;         /* (group order + 1)/2, so y*Q + y*Q = Q */
556     scalars[1] = y;
557
558     /* z is still the group order */
559     if (!TEST_true(EC_POINTs_mul(group, P, NULL, 2, points, scalars, ctx))
560         || !TEST_true(EC_POINTs_mul(group, R, z, 2, points, scalars, ctx))
561         || !TEST_int_eq(0, EC_POINT_cmp(group, P, R, ctx))
562         || !TEST_int_eq(0, EC_POINT_cmp(group, R, Q, ctx))
563         || !TEST_true(BN_rand(y, BN_num_bits(y), 0, 0))
564         || !TEST_true(BN_add(z, z, y)))
565         goto err;
566     BN_set_negative(z, 1);
567     scalars[0] = y;
568     scalars[1] = z;         /* z = -(order + y) */
569
570     if (!TEST_true(EC_POINTs_mul(group, P, NULL, 2, points, scalars, ctx))
571         || !TEST_true(EC_POINT_is_at_infinity(group, P))
572         || !TEST_true(BN_rand(x, BN_num_bits(y) - 1, 0, 0))
573         || !TEST_true(BN_add(z, x, y)))
574         goto err;
575     BN_set_negative(z, 1);
576     scalars[0] = x;
577     scalars[1] = y;
578     scalars[2] = z;         /* z = -(x+y) */
579
580     if (!TEST_ptr(scalar3 = BN_new()))
581         goto err;
582     BN_zero(scalar3);
583     scalars[3] = scalar3;
584
585     if (!TEST_true(EC_POINTs_mul(group, P, NULL, 4, points, scalars, ctx))
586         || !TEST_true(EC_POINT_is_at_infinity(group, P)))
587         goto err;
588 # endif
589     TEST_note(" ok\n");
590     r = 1;
591 err:
592     BN_CTX_free(ctx);
593     BN_free(p);
594     BN_free(a);
595     BN_free(b);
596     EC_GROUP_free(group);
597     EC_POINT_free(P);
598     EC_POINT_free(Q);
599     EC_POINT_free(R);
600     BN_free(x);
601     BN_free(y);
602     BN_free(z);
603     BN_free(yplusone);
604     BN_free(scalar3);
605     return r;
606 }
607
608 # ifndef OPENSSL_NO_EC2M
609
610 static struct c2_curve_test {
611     const char *name;
612     const char *p;
613     const char *a;
614     const char *b;
615     const char *x;
616     const char *y;
617     int ybit;
618     const char *order;
619     const char *cof;
620     int degree;
621 } char2_curve_tests[] = {
622     /* Curve K-163 (FIPS PUB 186-2, App. 6) */
623     {
624         "NIST curve K-163",
625         "0800000000000000000000000000000000000000C9",
626         "1",
627         "1",
628         "02FE13C0537BBC11ACAA07D793DE4E6D5E5C94EEE8",
629         "0289070FB05D38FF58321F2E800536D538CCDAA3D9",
630         1, "04000000000000000000020108A2E0CC0D99F8A5EF", "2", 163
631     },
632     /* Curve B-163 (FIPS PUB 186-2, App. 6) */
633     {
634         "NIST curve B-163",
635         "0800000000000000000000000000000000000000C9",
636         "1",
637         "020A601907B8C953CA1481EB10512F78744A3205FD",
638         "03F0EBA16286A2D57EA0991168D4994637E8343E36",
639         "00D51FBC6C71A0094FA2CDD545B11C5C0C797324F1",
640         1, "040000000000000000000292FE77E70C12A4234C33", "2", 163
641     },
642     /* Curve K-233 (FIPS PUB 186-2, App. 6) */
643     {
644         "NIST curve K-233",
645         "020000000000000000000000000000000000000004000000000000000001",
646         "0",
647         "1",
648         "017232BA853A7E731AF129F22FF4149563A419C26BF50A4C9D6EEFAD6126",
649         "01DB537DECE819B7F70F555A67C427A8CD9BF18AEB9B56E0C11056FAE6A3",
650         0,
651         "008000000000000000000000000000069D5BB915BCD46EFB1AD5F173ABDF",
652         "4", 233
653     },
654     /* Curve B-233 (FIPS PUB 186-2, App. 6) */
655     {
656         "NIST curve B-233",
657         "020000000000000000000000000000000000000004000000000000000001",
658         "000000000000000000000000000000000000000000000000000000000001",
659         "0066647EDE6C332C7F8C0923BB58213B333B20E9CE4281FE115F7D8F90AD",
660         "00FAC9DFCBAC8313BB2139F1BB755FEF65BC391F8B36F8F8EB7371FD558B",
661         "01006A08A41903350678E58528BEBF8A0BEFF867A7CA36716F7E01F81052",
662         1,
663         "01000000000000000000000000000013E974E72F8A6922031D2603CFE0D7",
664         "2", 233
665     },
666     /* Curve K-283 (FIPS PUB 186-2, App. 6) */
667     {
668         "NIST curve K-283",
669                                                                 "08000000"
670         "00000000000000000000000000000000000000000000000000000000000010A1",
671         "0",
672         "1",
673                                                                 "0503213F"
674         "78CA44883F1A3B8162F188E553CD265F23C1567A16876913B0C2AC2458492836",
675                                                                 "01CCDA38"
676         "0F1C9E318D90F95D07E5426FE87E45C0E8184698E45962364E34116177DD2259",
677         0,
678                                                                 "01FFFFFF"
679         "FFFFFFFFFFFFFFFFFFFFFFFFFFFFE9AE2ED07577265DFF7F94451E061E163C61",
680         "4", 283
681     },
682     /* Curve B-283 (FIPS PUB 186-2, App. 6) */
683     {
684         "NIST curve B-283",
685                                                                 "08000000"
686         "00000000000000000000000000000000000000000000000000000000000010A1",
687                                                                 "00000000"
688         "0000000000000000000000000000000000000000000000000000000000000001",
689                                                                 "027B680A"
690         "C8B8596DA5A4AF8A19A0303FCA97FD7645309FA2A581485AF6263E313B79A2F5",
691                                                                 "05F93925"
692         "8DB7DD90E1934F8C70B0DFEC2EED25B8557EAC9C80E2E198F8CDBECD86B12053",
693                                                                 "03676854"
694         "FE24141CB98FE6D4B20D02B4516FF702350EDDB0826779C813F0DF45BE8112F4",
695         1,
696                                                                 "03FFFFFF"
697         "FFFFFFFFFFFFFFFFFFFFFFFFFFFFEF90399660FC938A90165B042A7CEFADB307",
698         "2", 283
699     },
700     /* Curve K-409 (FIPS PUB 186-2, App. 6) */
701     {
702         "NIST curve K-409",
703                                 "0200000000000000000000000000000000000000"
704         "0000000000000000000000000000000000000000008000000000000000000001",
705         "0",
706         "1",
707                                 "0060F05F658F49C1AD3AB1890F7184210EFD0987"
708         "E307C84C27ACCFB8F9F67CC2C460189EB5AAAA62EE222EB1B35540CFE9023746",
709                                 "01E369050B7C4E42ACBA1DACBF04299C3460782F"
710         "918EA427E6325165E9EA10E3DA5F6C42E9C55215AA9CA27A5863EC48D8E0286B",
711         1,
712                                 "007FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
713         "FFFFFFFFFFFFFE5F83B2D4EA20400EC4557D5ED3E3E7CA5B4B5C83B8E01E5FCF",
714         "4", 409
715     },
716     /* Curve B-409 (FIPS PUB 186-2, App. 6) */
717     {
718         "NIST curve B-409",
719                                 "0200000000000000000000000000000000000000"
720         "0000000000000000000000000000000000000000008000000000000000000001",
721                                 "0000000000000000000000000000000000000000"
722         "0000000000000000000000000000000000000000000000000000000000000001",
723                                 "0021A5C2C8EE9FEB5C4B9A753B7B476B7FD6422E"
724         "F1F3DD674761FA99D6AC27C8A9A197B272822F6CD57A55AA4F50AE317B13545F",
725                                 "015D4860D088DDB3496B0C6064756260441CDE4A"
726         "F1771D4DB01FFE5B34E59703DC255A868A1180515603AEAB60794E54BB7996A7",
727                                 "0061B1CFAB6BE5F32BBFA78324ED106A7636B9C5"
728         "A7BD198D0158AA4F5488D08F38514F1FDF4B4F40D2181B3681C364BA0273C706",
729         1,
730                                 "0100000000000000000000000000000000000000"
731         "00000000000001E2AAD6A612F33307BE5FA47C3C9E052F838164CD37D9A21173",
732         "2", 409
733     },
734     /* Curve K-571 (FIPS PUB 186-2, App. 6) */
735     {
736         "NIST curve K-571",
737                                                          "800000000000000"
738         "0000000000000000000000000000000000000000000000000000000000000000"
739         "0000000000000000000000000000000000000000000000000000000000000425",
740         "0",
741         "1",
742                                                         "026EB7A859923FBC"
743         "82189631F8103FE4AC9CA2970012D5D46024804801841CA44370958493B205E6"
744         "47DA304DB4CEB08CBBD1BA39494776FB988B47174DCA88C7E2945283A01C8972",
745                                                         "0349DC807F4FBF37"
746         "4F4AEADE3BCA95314DD58CEC9F307A54FFC61EFC006D8A2C9D4979C0AC44AEA7"
747         "4FBEBBB9F772AEDCB620B01A7BA7AF1B320430C8591984F601CD4C143EF1C7A3",
748         0,
749                                                         "0200000000000000"
750         "00000000000000000000000000000000000000000000000000000000131850E1"
751         "F19A63E4B391A8DB917F4138B630D84BE5D639381E91DEB45CFE778F637C1001",
752         "4", 571
753     },
754     /* Curve B-571 (FIPS PUB 186-2, App. 6) */
755     {
756         "NIST curve B-571",
757                                                          "800000000000000"
758         "0000000000000000000000000000000000000000000000000000000000000000"
759         "0000000000000000000000000000000000000000000000000000000000000425",
760                                                         "0000000000000000"
761         "0000000000000000000000000000000000000000000000000000000000000000"
762         "0000000000000000000000000000000000000000000000000000000000000001",
763                                                         "02F40E7E2221F295"
764         "DE297117B7F3D62F5C6A97FFCB8CEFF1CD6BA8CE4A9A18AD84FFABBD8EFA5933"
765         "2BE7AD6756A66E294AFD185A78FF12AA520E4DE739BACA0C7FFEFF7F2955727A",
766                                                         "0303001D34B85629"
767         "6C16C0D40D3CD7750A93D1D2955FA80AA5F40FC8DB7B2ABDBDE53950F4C0D293"
768         "CDD711A35B67FB1499AE60038614F1394ABFA3B4C850D927E1E7769C8EEC2D19",
769                                                         "037BF27342DA639B"
770         "6DCCFFFEB73D69D78C6C27A6009CBBCA1980F8533921E8A684423E43BAB08A57"
771         "6291AF8F461BB2A8B3531D2F0485C19B16E2F1516E23DD3C1A4827AF1B8AC15B",
772         1,
773                                                         "03FFFFFFFFFFFFFF"
774         "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFE661CE18"
775         "FF55987308059B186823851EC7DD9CA1161DE93D5174D66E8382E9BB2FE84E47",
776         "2", 571
777     }
778 };
779
780 static int char2_curve_test(int n)
781 {
782     int r = 0;
783     BN_CTX *ctx = NULL;
784     BIGNUM *p = NULL, *a = NULL, *b = NULL;
785     BIGNUM *x = NULL, *y = NULL, *z = NULL, *cof = NULL, *yplusone = NULL;
786     EC_GROUP *group = NULL;
787     EC_POINT *P = NULL, *Q = NULL, *R = NULL;
788 # ifndef OPENSSL_NO_DEPRECATED_3_0
789     const EC_POINT *points[3];
790     const BIGNUM *scalars[3];
791 # endif
792     struct c2_curve_test *const test = char2_curve_tests + n;
793
794     if (!TEST_ptr(ctx = BN_CTX_new())
795         || !TEST_ptr(p = BN_new())
796         || !TEST_ptr(a = BN_new())
797         || !TEST_ptr(b = BN_new())
798         || !TEST_ptr(x = BN_new())
799         || !TEST_ptr(y = BN_new())
800         || !TEST_ptr(z = BN_new())
801         || !TEST_ptr(yplusone = BN_new())
802         || !TEST_true(BN_hex2bn(&p, test->p))
803         || !TEST_true(BN_hex2bn(&a, test->a))
804         || !TEST_true(BN_hex2bn(&b, test->b))
805         || !TEST_true(group = EC_GROUP_new_curve_GF2m(p, a, b, ctx))
806         || !TEST_ptr(P = EC_POINT_new(group))
807         || !TEST_ptr(Q = EC_POINT_new(group))
808         || !TEST_ptr(R = EC_POINT_new(group))
809         || !TEST_true(BN_hex2bn(&x, test->x))
810         || !TEST_true(BN_hex2bn(&y, test->y))
811         || !TEST_true(BN_add(yplusone, y, BN_value_one())))
812         goto err;
813
814 /* Change test based on whether binary point compression is enabled or not. */
815 # ifdef OPENSSL_EC_BIN_PT_COMP
816     /*
817      * When (x, y) is on the curve, (x, y + 1) is, as it happens, not,
818      * and therefore setting the coordinates should fail.
819      */
820     if (!TEST_false(EC_POINT_set_affine_coordinates(group, P, x, yplusone, ctx))
821         || !TEST_true(EC_POINT_set_compressed_coordinates(group, P, x,
822                                                           test->y_bit,
823                                                           ctx))
824         || !TEST_int_gt(EC_POINT_is_on_curve(group, P, ctx), 0)
825         || !TEST_true(BN_hex2bn(&z, test->order))
826         || !TEST_true(BN_hex2bn(&cof, test->cof))
827         || !TEST_true(EC_GROUP_set_generator(group, P, z, cof))
828         || !TEST_true(EC_POINT_get_affine_coordinates(group, P, x, y, ctx)))
829         goto err;
830     TEST_info("%s -- Generator", test->name);
831     test_output_bignum("x", x);
832     test_output_bignum("y", y);
833     /* G_y value taken from the standard: */
834     if (!TEST_true(BN_hex2bn(&z, test->y))
835         || !TEST_BN_eq(y, z))
836         goto err;
837 # else
838     /*
839      * When (x, y) is on the curve, (x, y + 1) is, as it happens, not,
840      * and therefore setting the coordinates should fail.
841      */
842     if (!TEST_false(EC_POINT_set_affine_coordinates(group, P, x, yplusone, ctx))
843         || !TEST_true(EC_POINT_set_affine_coordinates(group, P, x, y, ctx))
844         || !TEST_int_gt(EC_POINT_is_on_curve(group, P, ctx), 0)
845         || !TEST_true(BN_hex2bn(&z, test->order))
846         || !TEST_true(BN_hex2bn(&cof, test->cof))
847         || !TEST_true(EC_GROUP_set_generator(group, P, z, cof)))
848         goto err;
849     TEST_info("%s -- Generator:", test->name);
850     test_output_bignum("x", x);
851     test_output_bignum("y", y);
852 # endif
853
854     if (!TEST_int_eq(EC_GROUP_get_degree(group), test->degree)
855         || !group_order_tests(group))
856         goto err;
857
858     /* more tests using the last curve */
859     if (n == OSSL_NELEM(char2_curve_tests) - 1) {
860         if (!TEST_true(EC_POINT_set_affine_coordinates(group, P, x, y, ctx))
861             || !TEST_true(EC_POINT_copy(Q, P))
862             || !TEST_false(EC_POINT_is_at_infinity(group, Q))
863             || !TEST_true(EC_POINT_dbl(group, P, P, ctx))
864             || !TEST_int_gt(EC_POINT_is_on_curve(group, P, ctx), 0)
865             || !TEST_true(EC_POINT_invert(group, Q, ctx))       /* P = -2Q */
866             || !TEST_true(EC_POINT_add(group, R, P, Q, ctx))
867             || !TEST_true(EC_POINT_add(group, R, R, Q, ctx))
868             || !TEST_true(EC_POINT_is_at_infinity(group, R))   /* R = P + 2Q */
869             || !TEST_false(EC_POINT_is_at_infinity(group, Q)))
870             goto err;
871
872 # ifndef OPENSSL_NO_DEPRECATED_3_0
873         TEST_note("combined multiplication ...");
874         points[0] = Q;
875         points[1] = Q;
876         points[2] = Q;
877
878         if (!TEST_true(BN_add(y, z, BN_value_one()))
879             || !TEST_BN_even(y)
880             || !TEST_true(BN_rshift1(y, y)))
881             goto err;
882         scalars[0] = y;         /* (group order + 1)/2, so y*Q + y*Q = Q */
883         scalars[1] = y;
884
885         /* z is still the group order */
886         if (!TEST_true(EC_POINTs_mul(group, P, NULL, 2, points, scalars, ctx))
887             || !TEST_true(EC_POINTs_mul(group, R, z, 2, points, scalars, ctx))
888             || !TEST_int_eq(0, EC_POINT_cmp(group, P, R, ctx))
889             || !TEST_int_eq(0, EC_POINT_cmp(group, R, Q, ctx)))
890             goto err;
891
892         if (!TEST_true(BN_rand(y, BN_num_bits(y), 0, 0))
893             || !TEST_true(BN_add(z, z, y)))
894             goto err;
895         BN_set_negative(z, 1);
896         scalars[0] = y;
897         scalars[1] = z;         /* z = -(order + y) */
898
899         if (!TEST_true(EC_POINTs_mul(group, P, NULL, 2, points, scalars, ctx))
900             || !TEST_true(EC_POINT_is_at_infinity(group, P)))
901             goto err;
902
903         if (!TEST_true(BN_rand(x, BN_num_bits(y) - 1, 0, 0))
904             || !TEST_true(BN_add(z, x, y)))
905             goto err;
906         BN_set_negative(z, 1);
907         scalars[0] = x;
908         scalars[1] = y;
909         scalars[2] = z;         /* z = -(x+y) */
910
911         if (!TEST_true(EC_POINTs_mul(group, P, NULL, 3, points, scalars, ctx))
912             || !TEST_true(EC_POINT_is_at_infinity(group, P)))
913             goto err;
914 # endif
915     }
916
917     r = 1;
918 err:
919     BN_CTX_free(ctx);
920     BN_free(p);
921     BN_free(a);
922     BN_free(b);
923     BN_free(x);
924     BN_free(y);
925     BN_free(z);
926     BN_free(yplusone);
927     BN_free(cof);
928     EC_POINT_free(P);
929     EC_POINT_free(Q);
930     EC_POINT_free(R);
931     EC_GROUP_free(group);
932     return r;
933 }
934
935 static int char2_field_tests(void)
936 {
937     BN_CTX *ctx = NULL;
938     BIGNUM *p = NULL, *a = NULL, *b = NULL;
939     EC_GROUP *group = NULL;
940     EC_POINT *P = NULL, *Q = NULL, *R = NULL;
941     BIGNUM *x = NULL, *y = NULL, *z = NULL, *cof = NULL, *yplusone = NULL;
942     unsigned char buf[100];
943     size_t len;
944     int k, r = 0;
945
946     if (!TEST_ptr(ctx = BN_CTX_new())
947         || !TEST_ptr(p = BN_new())
948         || !TEST_ptr(a = BN_new())
949         || !TEST_ptr(b = BN_new())
950         || !TEST_true(BN_hex2bn(&p, "13"))
951         || !TEST_true(BN_hex2bn(&a, "3"))
952         || !TEST_true(BN_hex2bn(&b, "1")))
953         goto err;
954
955     if (!TEST_ptr(group = EC_GROUP_new_curve_GF2m(p, a, b, ctx))
956         || !TEST_true(EC_GROUP_get_curve(group, p, a, b, ctx)))
957         goto err;
958
959     TEST_info("Curve defined by Weierstrass equation");
960     TEST_note("     y^2 + x*y = x^3 + a*x^2 + b (mod p)");
961     test_output_bignum("a", a);
962     test_output_bignum("b", b);
963     test_output_bignum("p", p);
964
965      if (!TEST_ptr(P = EC_POINT_new(group))
966         || !TEST_ptr(Q = EC_POINT_new(group))
967         || !TEST_ptr(R = EC_POINT_new(group))
968         || !TEST_true(EC_POINT_set_to_infinity(group, P))
969         || !TEST_true(EC_POINT_is_at_infinity(group, P)))
970         goto err;
971
972     buf[0] = 0;
973     if (!TEST_true(EC_POINT_oct2point(group, Q, buf, 1, ctx))
974         || !TEST_true(EC_POINT_add(group, P, P, Q, ctx))
975         || !TEST_true(EC_POINT_is_at_infinity(group, P))
976         || !TEST_ptr(x = BN_new())
977         || !TEST_ptr(y = BN_new())
978         || !TEST_ptr(z = BN_new())
979         || !TEST_ptr(cof = BN_new())
980         || !TEST_ptr(yplusone = BN_new())
981         || !TEST_true(BN_hex2bn(&x, "6"))
982 /* Change test based on whether binary point compression is enabled or not. */
983 #  ifdef OPENSSL_EC_BIN_PT_COMP
984         || !TEST_true(EC_POINT_set_compressed_coordinates(group, Q, x, 1, ctx))
985 #  else
986         || !TEST_true(BN_hex2bn(&y, "8"))
987         || !TEST_true(EC_POINT_set_affine_coordinates(group, Q, x, y, ctx))
988 #  endif
989        )
990         goto err;
991     if (!TEST_int_gt(EC_POINT_is_on_curve(group, Q, ctx), 0)) {
992 /* Change test based on whether binary point compression is enabled or not. */
993 #  ifdef OPENSSL_EC_BIN_PT_COMP
994         if (!TEST_true(EC_POINT_get_affine_coordinates(group, Q, x, y, ctx)))
995             goto err;
996 #  endif
997         TEST_info("Point is not on curve");
998         test_output_bignum("x", x);
999         test_output_bignum("y", y);
1000         goto err;
1001     }
1002
1003     TEST_note("A cyclic subgroup:");
1004     k = 100;
1005     do {
1006         if (!TEST_int_ne(k--, 0))
1007             goto err;
1008
1009         if (EC_POINT_is_at_infinity(group, P))
1010             TEST_note("     point at infinity");
1011         else {
1012             if (!TEST_true(EC_POINT_get_affine_coordinates(group, P, x, y,
1013                                                            ctx)))
1014                 goto err;
1015
1016             test_output_bignum("x", x);
1017             test_output_bignum("y", y);
1018         }
1019
1020         if (!TEST_true(EC_POINT_copy(R, P))
1021             || !TEST_true(EC_POINT_add(group, P, P, Q, ctx)))
1022             goto err;
1023     }
1024     while (!EC_POINT_is_at_infinity(group, P));
1025
1026     if (!TEST_true(EC_POINT_add(group, P, Q, R, ctx))
1027         || !TEST_true(EC_POINT_is_at_infinity(group, P)))
1028         goto err;
1029
1030 /* Change test based on whether binary point compression is enabled or not. */
1031 #  ifdef OPENSSL_EC_BIN_PT_COMP
1032     len = EC_POINT_point2oct(group, Q, POINT_CONVERSION_COMPRESSED,
1033                              buf, sizeof(buf), ctx);
1034     if (!TEST_size_t_ne(len, 0)
1035         || !TEST_true(EC_POINT_oct2point(group, P, buf, len, ctx))
1036         || !TEST_int_eq(0, EC_POINT_cmp(group, P, Q, ctx)))
1037         goto err;
1038     test_output_memory("Generator as octet string, compressed form:",
1039                        buf, len);
1040 #  endif
1041
1042     len = EC_POINT_point2oct(group, Q, POINT_CONVERSION_UNCOMPRESSED,
1043                              buf, sizeof(buf), ctx);
1044     if (!TEST_size_t_ne(len, 0)
1045         || !TEST_true(EC_POINT_oct2point(group, P, buf, len, ctx))
1046         || !TEST_int_eq(0, EC_POINT_cmp(group, P, Q, ctx)))
1047         goto err;
1048     test_output_memory("Generator as octet string, uncompressed form:",
1049                        buf, len);
1050
1051 /* Change test based on whether binary point compression is enabled or not. */
1052 #  ifdef OPENSSL_EC_BIN_PT_COMP
1053     len =
1054         EC_POINT_point2oct(group, Q, POINT_CONVERSION_HYBRID, buf, sizeof(buf),
1055                            ctx);
1056     if (!TEST_size_t_ne(len, 0)
1057         || !TEST_true(EC_POINT_oct2point(group, P, buf, len, ctx))
1058         || !TEST_int_eq(0, EC_POINT_cmp(group, P, Q, ctx)))
1059         goto err;
1060     test_output_memory("Generator as octet string, hybrid form:",
1061                        buf, len);
1062 #  endif
1063
1064     if (!TEST_true(EC_POINT_invert(group, P, ctx))
1065         || !TEST_int_eq(0, EC_POINT_cmp(group, P, R, ctx)))
1066         goto err;
1067
1068     TEST_note("\n");
1069
1070     r = 1;
1071 err:
1072     BN_CTX_free(ctx);
1073     BN_free(p);
1074     BN_free(a);
1075     BN_free(b);
1076     EC_GROUP_free(group);
1077     EC_POINT_free(P);
1078     EC_POINT_free(Q);
1079     EC_POINT_free(R);
1080     BN_free(x);
1081     BN_free(y);
1082     BN_free(z);
1083     BN_free(cof);
1084     BN_free(yplusone);
1085     return r;
1086 }
1087 # endif
1088
1089 static int internal_curve_test(int n)
1090 {
1091     EC_GROUP *group = NULL;
1092     int nid = curves[n].nid;
1093
1094     if (!TEST_ptr(group = EC_GROUP_new_by_curve_name(nid))) {
1095         TEST_info("EC_GROUP_new_curve_name() failed with curve %s\n",
1096                   OBJ_nid2sn(nid));
1097         return 0;
1098     }
1099     if (!TEST_true(EC_GROUP_check(group, NULL))) {
1100         TEST_info("EC_GROUP_check() failed with curve %s\n", OBJ_nid2sn(nid));
1101         EC_GROUP_free(group);
1102         return 0;
1103     }
1104     EC_GROUP_free(group);
1105     return 1;
1106 }
1107
1108 static int internal_curve_test_method(int n)
1109 {
1110     int r, nid = curves[n].nid;
1111     EC_GROUP *group;
1112
1113     if (!TEST_ptr(group = EC_GROUP_new_by_curve_name(nid))) {
1114         TEST_info("Curve %s failed\n", OBJ_nid2sn(nid));
1115         return 0;
1116     }
1117     r = group_order_tests(group);
1118     EC_GROUP_free(group);
1119     return r;
1120 }
1121
1122 static int group_field_test(void)
1123 {
1124     int r = 1;
1125     BIGNUM *secp521r1_field = NULL;
1126     BIGNUM *sect163r2_field = NULL;
1127     EC_GROUP *secp521r1_group = NULL;
1128     EC_GROUP *sect163r2_group = NULL;
1129
1130     BN_hex2bn(&secp521r1_field,
1131                 "01FFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
1132                 "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
1133                 "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
1134                 "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
1135                 "FFFF");
1136
1137
1138     BN_hex2bn(&sect163r2_field,
1139                 "08000000000000000000000000000000"
1140                 "00000000C9");
1141
1142     secp521r1_group = EC_GROUP_new_by_curve_name(NID_secp521r1);
1143     if (BN_cmp(secp521r1_field, EC_GROUP_get0_field(secp521r1_group)))
1144       r = 0;
1145
1146     # ifndef OPENSSL_NO_EC2M
1147     sect163r2_group = EC_GROUP_new_by_curve_name(NID_sect163r2);
1148     if (BN_cmp(sect163r2_field, EC_GROUP_get0_field(sect163r2_group)))
1149       r = 0;
1150     # endif
1151
1152     EC_GROUP_free(secp521r1_group);
1153     EC_GROUP_free(sect163r2_group);
1154     BN_free(secp521r1_field);
1155     BN_free(sect163r2_field);
1156     return r;
1157 }
1158
1159 /*
1160  * nistp_test_params contains magic numbers for testing
1161  * several NIST curves with characteristic > 3.
1162  */
1163 struct nistp_test_params {
1164     const int nid;
1165     int degree;
1166     /*
1167      * Qx, Qy and D are taken from
1168      * http://csrc.nist.gov/groups/ST/toolkit/documents/Examples/ECDSA_Prime.pdf
1169      * Otherwise, values are standard curve parameters from FIPS 180-3
1170      */
1171     const char *p, *a, *b, *Qx, *Qy, *Gx, *Gy, *order, *d;
1172 };
1173
1174 static const struct nistp_test_params nistp_tests_params[] = {
1175     {
1176      /* P-224 */
1177      NID_secp224r1,
1178      224,
1179      /* p */
1180      "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF000000000000000000000001",
1181      /* a */
1182      "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFFFFFFFFFFFFFFFFFFFE",
1183      /* b */
1184      "B4050A850C04B3ABF54132565044B0B7D7BFD8BA270B39432355FFB4",
1185      /* Qx */
1186      "E84FB0B8E7000CB657D7973CF6B42ED78B301674276DF744AF130B3E",
1187      /* Qy */
1188      "4376675C6FC5612C21A0FF2D2A89D2987DF7A2BC52183B5982298555",
1189      /* Gx */
1190      "B70E0CBD6BB4BF7F321390B94A03C1D356C21122343280D6115C1D21",
1191      /* Gy */
1192      "BD376388B5F723FB4C22DFE6CD4375A05A07476444D5819985007E34",
1193      /* order */
1194      "FFFFFFFFFFFFFFFFFFFFFFFFFFFF16A2E0B8F03E13DD29455C5C2A3D",
1195      /* d */
1196      "3F0C488E987C80BE0FEE521F8D90BE6034EC69AE11CA72AA777481E8",
1197      },
1198     {
1199      /* P-256 */
1200      NID_X9_62_prime256v1,
1201      256,
1202      /* p */
1203      "ffffffff00000001000000000000000000000000ffffffffffffffffffffffff",
1204      /* a */
1205      "ffffffff00000001000000000000000000000000fffffffffffffffffffffffc",
1206      /* b */
1207      "5ac635d8aa3a93e7b3ebbd55769886bc651d06b0cc53b0f63bce3c3e27d2604b",
1208      /* Qx */
1209      "b7e08afdfe94bad3f1dc8c734798ba1c62b3a0ad1e9ea2a38201cd0889bc7a19",
1210      /* Qy */
1211      "3603f747959dbf7a4bb226e41928729063adc7ae43529e61b563bbc606cc5e09",
1212      /* Gx */
1213      "6b17d1f2e12c4247f8bce6e563a440f277037d812deb33a0f4a13945d898c296",
1214      /* Gy */
1215      "4fe342e2fe1a7f9b8ee7eb4a7c0f9e162bce33576b315ececbb6406837bf51f5",
1216      /* order */
1217      "ffffffff00000000ffffffffffffffffbce6faada7179e84f3b9cac2fc632551",
1218      /* d */
1219      "c477f9f65c22cce20657faa5b2d1d8122336f851a508a1ed04e479c34985bf96",
1220      },
1221     {
1222      /* P-521 */
1223      NID_secp521r1,
1224      521,
1225      /* p */
1226                                                                   "1ff"
1227      "ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff"
1228      "ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff",
1229      /* a */
1230                                                                   "1ff"
1231      "ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff"
1232      "fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffc",
1233      /* b */
1234                                                                   "051"
1235      "953eb9618e1c9a1f929a21a0b68540eea2da725b99b315f3b8b489918ef109e1"
1236      "56193951ec7e937b1652c0bd3bb1bf073573df883d2c34f1ef451fd46b503f00",
1237      /* Qx */
1238                                                                  "0098"
1239      "e91eef9a68452822309c52fab453f5f117c1da8ed796b255e9ab8f6410cca16e"
1240      "59df403a6bdc6ca467a37056b1e54b3005d8ac030decfeb68df18b171885d5c4",
1241      /* Qy */
1242                                                                  "0164"
1243      "350c321aecfc1cca1ba4364c9b15656150b4b78d6a48d7d28e7f31985ef17be8"
1244      "554376b72900712c4b83ad668327231526e313f5f092999a4632fd50d946bc2e",
1245      /* Gx */
1246                                                                    "c6"
1247      "858e06b70404e9cd9e3ecb662395b4429c648139053fb521f828af606b4d3dba"
1248      "a14b5e77efe75928fe1dc127a2ffa8de3348b3c1856a429bf97e7e31c2e5bd66",
1249      /* Gy */
1250                                                                   "118"
1251      "39296a789a3bc0045c8a5fb42c7d1bd998f54449579b446817afbd17273e662c"
1252      "97ee72995ef42640c550b9013fad0761353c7086a272c24088be94769fd16650",
1253      /* order */
1254                                                                   "1ff"
1255      "fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffa"
1256      "51868783bf2f966b7fcc0148f709a5d03bb5c9b8899c47aebb6fb71e91386409",
1257      /* d */
1258                                                                  "0100"
1259      "085f47b8e1b8b11b7eb33028c0b2888e304bfc98501955b45bba1478dc184eee"
1260      "df09b86a5f7c21994406072787205e69a63709fe35aa93ba333514b24f961722",
1261      },
1262 };
1263
1264 static int nistp_single_test(int idx)
1265 {
1266     const struct nistp_test_params *test = nistp_tests_params + idx;
1267     BN_CTX *ctx = NULL;
1268     BIGNUM *p = NULL, *a = NULL, *b = NULL, *x = NULL, *y = NULL;
1269     BIGNUM *n = NULL, *m = NULL, *order = NULL, *yplusone = NULL;
1270     EC_GROUP *NISTP = NULL;
1271     EC_POINT *G = NULL, *P = NULL, *Q = NULL, *Q_CHECK = NULL;
1272     int r = 0;
1273
1274     TEST_note("NIST curve P-%d (optimised implementation):",
1275               test->degree);
1276     if (!TEST_ptr(ctx = BN_CTX_new())
1277         || !TEST_ptr(p = BN_new())
1278         || !TEST_ptr(a = BN_new())
1279         || !TEST_ptr(b = BN_new())
1280         || !TEST_ptr(x = BN_new())
1281         || !TEST_ptr(y = BN_new())
1282         || !TEST_ptr(m = BN_new())
1283         || !TEST_ptr(n = BN_new())
1284         || !TEST_ptr(order = BN_new())
1285         || !TEST_ptr(yplusone = BN_new())
1286
1287         || !TEST_ptr(NISTP = EC_GROUP_new_by_curve_name(test->nid))
1288         || !TEST_true(BN_hex2bn(&p, test->p))
1289         || !TEST_int_eq(1, BN_check_prime(p, ctx, NULL))
1290         || !TEST_true(BN_hex2bn(&a, test->a))
1291         || !TEST_true(BN_hex2bn(&b, test->b))
1292         || !TEST_true(EC_GROUP_set_curve(NISTP, p, a, b, ctx))
1293         || !TEST_ptr(G = EC_POINT_new(NISTP))
1294         || !TEST_ptr(P = EC_POINT_new(NISTP))
1295         || !TEST_ptr(Q = EC_POINT_new(NISTP))
1296         || !TEST_ptr(Q_CHECK = EC_POINT_new(NISTP))
1297         || !TEST_true(BN_hex2bn(&x, test->Qx))
1298         || !TEST_true(BN_hex2bn(&y, test->Qy))
1299         || !TEST_true(BN_add(yplusone, y, BN_value_one()))
1300     /*
1301      * When (x, y) is on the curve, (x, y + 1) is, as it happens, not,
1302      * and therefore setting the coordinates should fail.
1303      */
1304         || !TEST_false(EC_POINT_set_affine_coordinates(NISTP, Q_CHECK, x,
1305                                                        yplusone, ctx))
1306         || !TEST_true(EC_POINT_set_affine_coordinates(NISTP, Q_CHECK, x, y,
1307                                                       ctx))
1308         || !TEST_true(BN_hex2bn(&x, test->Gx))
1309         || !TEST_true(BN_hex2bn(&y, test->Gy))
1310         || !TEST_true(EC_POINT_set_affine_coordinates(NISTP, G, x, y, ctx))
1311         || !TEST_true(BN_hex2bn(&order, test->order))
1312         || !TEST_true(EC_GROUP_set_generator(NISTP, G, order, BN_value_one()))
1313         || !TEST_int_eq(EC_GROUP_get_degree(NISTP), test->degree))
1314         goto err;
1315
1316     TEST_note("NIST test vectors ... ");
1317     if (!TEST_true(BN_hex2bn(&n, test->d)))
1318         goto err;
1319     /* fixed point multiplication */
1320     EC_POINT_mul(NISTP, Q, n, NULL, NULL, ctx);
1321     if (!TEST_int_eq(0, EC_POINT_cmp(NISTP, Q, Q_CHECK, ctx)))
1322         goto err;
1323     /* random point multiplication */
1324     EC_POINT_mul(NISTP, Q, NULL, G, n, ctx);
1325     if (!TEST_int_eq(0, EC_POINT_cmp(NISTP, Q, Q_CHECK, ctx))
1326
1327         /* set generator to P = 2*G, where G is the standard generator */
1328         || !TEST_true(EC_POINT_dbl(NISTP, P, G, ctx))
1329         || !TEST_true(EC_GROUP_set_generator(NISTP, P, order, BN_value_one()))
1330         /* set the scalar to m=n/2, where n is the NIST test scalar */
1331         || !TEST_true(BN_rshift(m, n, 1)))
1332         goto err;
1333
1334     /* test the non-standard generator */
1335     /* fixed point multiplication */
1336     EC_POINT_mul(NISTP, Q, m, NULL, NULL, ctx);
1337     if (!TEST_int_eq(0, EC_POINT_cmp(NISTP, Q, Q_CHECK, ctx)))
1338         goto err;
1339     /* random point multiplication */
1340     EC_POINT_mul(NISTP, Q, NULL, P, m, ctx);
1341     if (!TEST_int_eq(0, EC_POINT_cmp(NISTP, Q, Q_CHECK, ctx))
1342 # ifndef OPENSSL_NO_DEPRECATED_3_0
1343         /* We have not performed precomp so this should be false */
1344         || !TEST_false(EC_GROUP_have_precompute_mult(NISTP))
1345         /* now repeat all tests with precomputation */
1346         || !TEST_true(EC_GROUP_precompute_mult(NISTP, ctx))
1347 # endif
1348         )
1349         goto err;
1350
1351     /* fixed point multiplication */
1352     EC_POINT_mul(NISTP, Q, m, NULL, NULL, ctx);
1353     if (!TEST_int_eq(0, EC_POINT_cmp(NISTP, Q, Q_CHECK, ctx)))
1354         goto err;
1355     /* random point multiplication */
1356     EC_POINT_mul(NISTP, Q, NULL, P, m, ctx);
1357     if (!TEST_int_eq(0, EC_POINT_cmp(NISTP, Q, Q_CHECK, ctx))
1358
1359     /* reset generator */
1360         || !TEST_true(EC_GROUP_set_generator(NISTP, G, order, BN_value_one())))
1361         goto err;
1362     /* fixed point multiplication */
1363     EC_POINT_mul(NISTP, Q, n, NULL, NULL, ctx);
1364     if (!TEST_int_eq(0, EC_POINT_cmp(NISTP, Q, Q_CHECK, ctx)))
1365         goto err;
1366     /* random point multiplication */
1367     EC_POINT_mul(NISTP, Q, NULL, G, n, ctx);
1368     if (!TEST_int_eq(0, EC_POINT_cmp(NISTP, Q, Q_CHECK, ctx)))
1369         goto err;
1370
1371     /* regression test for felem_neg bug */
1372     if (!TEST_true(BN_set_word(m, 32))
1373         || !TEST_true(BN_set_word(n, 31))
1374         || !TEST_true(EC_POINT_copy(P, G))
1375         || !TEST_true(EC_POINT_invert(NISTP, P, ctx))
1376         || !TEST_true(EC_POINT_mul(NISTP, Q, m, P, n, ctx))
1377         || !TEST_int_eq(0, EC_POINT_cmp(NISTP, Q, G, ctx)))
1378       goto err;
1379
1380     r = 1;
1381 err:
1382     EC_GROUP_free(NISTP);
1383     EC_POINT_free(G);
1384     EC_POINT_free(P);
1385     EC_POINT_free(Q);
1386     EC_POINT_free(Q_CHECK);
1387     BN_free(n);
1388     BN_free(m);
1389     BN_free(p);
1390     BN_free(a);
1391     BN_free(b);
1392     BN_free(x);
1393     BN_free(y);
1394     BN_free(order);
1395     BN_free(yplusone);
1396     BN_CTX_free(ctx);
1397     return r;
1398 }
1399
1400 static const unsigned char p521_named[] = {
1401     0x06, 0x05, 0x2b, 0x81, 0x04, 0x00, 0x23,
1402 };
1403
1404 static const unsigned char p521_explicit[] = {
1405     0x30, 0x82, 0x01, 0xc3, 0x02, 0x01, 0x01, 0x30, 0x4d, 0x06, 0x07, 0x2a,
1406     0x86, 0x48, 0xce, 0x3d, 0x01, 0x01, 0x02, 0x42, 0x01, 0xff, 0xff, 0xff,
1407     0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
1408     0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
1409     0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
1410     0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
1411     0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
1412     0xff, 0xff, 0x30, 0x81, 0x9f, 0x04, 0x42, 0x01, 0xff, 0xff, 0xff, 0xff,
1413     0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
1414     0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
1415     0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
1416     0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
1417     0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
1418     0xfc, 0x04, 0x42, 0x00, 0x51, 0x95, 0x3e, 0xb9, 0x61, 0x8e, 0x1c, 0x9a,
1419     0x1f, 0x92, 0x9a, 0x21, 0xa0, 0xb6, 0x85, 0x40, 0xee, 0xa2, 0xda, 0x72,
1420     0x5b, 0x99, 0xb3, 0x15, 0xf3, 0xb8, 0xb4, 0x89, 0x91, 0x8e, 0xf1, 0x09,
1421     0xe1, 0x56, 0x19, 0x39, 0x51, 0xec, 0x7e, 0x93, 0x7b, 0x16, 0x52, 0xc0,
1422     0xbd, 0x3b, 0xb1, 0xbf, 0x07, 0x35, 0x73, 0xdf, 0x88, 0x3d, 0x2c, 0x34,
1423     0xf1, 0xef, 0x45, 0x1f, 0xd4, 0x6b, 0x50, 0x3f, 0x00, 0x03, 0x15, 0x00,
1424     0xd0, 0x9e, 0x88, 0x00, 0x29, 0x1c, 0xb8, 0x53, 0x96, 0xcc, 0x67, 0x17,
1425     0x39, 0x32, 0x84, 0xaa, 0xa0, 0xda, 0x64, 0xba, 0x04, 0x81, 0x85, 0x04,
1426     0x00, 0xc6, 0x85, 0x8e, 0x06, 0xb7, 0x04, 0x04, 0xe9, 0xcd, 0x9e, 0x3e,
1427     0xcb, 0x66, 0x23, 0x95, 0xb4, 0x42, 0x9c, 0x64, 0x81, 0x39, 0x05, 0x3f,
1428     0xb5, 0x21, 0xf8, 0x28, 0xaf, 0x60, 0x6b, 0x4d, 0x3d, 0xba, 0xa1, 0x4b,
1429     0x5e, 0x77, 0xef, 0xe7, 0x59, 0x28, 0xfe, 0x1d, 0xc1, 0x27, 0xa2, 0xff,
1430     0xa8, 0xde, 0x33, 0x48, 0xb3, 0xc1, 0x85, 0x6a, 0x42, 0x9b, 0xf9, 0x7e,
1431     0x7e, 0x31, 0xc2, 0xe5, 0xbd, 0x66, 0x01, 0x18, 0x39, 0x29, 0x6a, 0x78,
1432     0x9a, 0x3b, 0xc0, 0x04, 0x5c, 0x8a, 0x5f, 0xb4, 0x2c, 0x7d, 0x1b, 0xd9,
1433     0x98, 0xf5, 0x44, 0x49, 0x57, 0x9b, 0x44, 0x68, 0x17, 0xaf, 0xbd, 0x17,
1434     0x27, 0x3e, 0x66, 0x2c, 0x97, 0xee, 0x72, 0x99, 0x5e, 0xf4, 0x26, 0x40,
1435     0xc5, 0x50, 0xb9, 0x01, 0x3f, 0xad, 0x07, 0x61, 0x35, 0x3c, 0x70, 0x86,
1436     0xa2, 0x72, 0xc2, 0x40, 0x88, 0xbe, 0x94, 0x76, 0x9f, 0xd1, 0x66, 0x50,
1437     0x02, 0x42, 0x01, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
1438     0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
1439     0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfa,
1440     0x51, 0x86, 0x87, 0x83, 0xbf, 0x2f, 0x96, 0x6b, 0x7f, 0xcc, 0x01, 0x48,
1441     0xf7, 0x09, 0xa5, 0xd0, 0x3b, 0xb5, 0xc9, 0xb8, 0x89, 0x9c, 0x47, 0xae,
1442     0xbb, 0x6f, 0xb7, 0x1e, 0x91, 0x38, 0x64, 0x09, 0x02, 0x01, 0x01,
1443 };
1444
1445 /*
1446  * This test validates a named curve's group parameters using
1447  * EC_GROUP_check_named_curve(). It also checks that modifying any of the
1448  * group parameters results in the curve not being valid.
1449  */
1450 static int check_named_curve_test(int id)
1451 {
1452     int ret = 0, nid, field_nid, has_seed;
1453     EC_GROUP *group = NULL, *gtest = NULL;
1454     const EC_POINT *group_gen = NULL;
1455     EC_POINT *other_gen = NULL;
1456     BIGNUM *group_p = NULL, *group_a = NULL, *group_b = NULL;
1457     BIGNUM *other_p = NULL, *other_a = NULL, *other_b = NULL;
1458     BIGNUM *group_cofactor = NULL, *other_cofactor = NULL;
1459     BIGNUM *other_order = NULL;
1460     const BIGNUM *group_order = NULL;
1461     BN_CTX *bn_ctx = NULL;
1462     static const unsigned char invalid_seed[] = "THIS IS NOT A VALID SEED";
1463     static size_t invalid_seed_len = sizeof(invalid_seed);
1464
1465     /* Do some setup */
1466     nid = curves[id].nid;
1467     if (!TEST_ptr(bn_ctx = BN_CTX_new())
1468         || !TEST_ptr(group = EC_GROUP_new_by_curve_name(nid))
1469         || !TEST_ptr(gtest = EC_GROUP_dup(group))
1470         || !TEST_ptr(group_p = BN_new())
1471         || !TEST_ptr(group_a = BN_new())
1472         || !TEST_ptr(group_b = BN_new())
1473         || !TEST_ptr(group_cofactor = BN_new())
1474         || !TEST_ptr(group_gen = EC_GROUP_get0_generator(group))
1475         || !TEST_ptr(group_order = EC_GROUP_get0_order(group))
1476         || !TEST_true(EC_GROUP_get_cofactor(group, group_cofactor, NULL))
1477         || !TEST_true(EC_GROUP_get_curve(group, group_p, group_a, group_b, NULL))
1478         || !TEST_ptr(other_gen = EC_POINT_dup(group_gen, group))
1479         || !TEST_true(EC_POINT_add(group, other_gen, group_gen, group_gen, NULL))
1480         || !TEST_ptr(other_order = BN_dup(group_order))
1481         || !TEST_true(BN_add_word(other_order, 1))
1482         || !TEST_ptr(other_a = BN_dup(group_a))
1483         || !TEST_true(BN_add_word(other_a, 1))
1484         || !TEST_ptr(other_b = BN_dup(group_b))
1485         || !TEST_true(BN_add_word(other_b, 1))
1486         || !TEST_ptr(other_cofactor = BN_dup(group_cofactor))
1487         || !TEST_true(BN_add_word(other_cofactor, 1)))
1488         goto err;
1489
1490     /* Determine if the built-in curve has a seed field set */
1491     has_seed = (EC_GROUP_get_seed_len(group) > 0);
1492     field_nid = EC_GROUP_get_field_type(group);
1493     if (field_nid == NID_X9_62_characteristic_two_field) {
1494         if (!TEST_ptr(other_p = BN_dup(group_p))
1495             || !TEST_true(BN_lshift1(other_p, other_p)))
1496             goto err;
1497     } else {
1498         if (!TEST_ptr(other_p = BN_dup(group_p)))
1499             goto err;
1500         /*
1501          * Just choosing any arbitrary prime does not work..
1502          * Setting p via ec_GFp_nist_group_set_curve() needs the prime to be a
1503          * nist prime. So only select one of these as an alternate prime.
1504          */
1505         if (!TEST_ptr(BN_copy(other_p,
1506                               BN_ucmp(BN_get0_nist_prime_192(), other_p) == 0 ?
1507                                       BN_get0_nist_prime_256() :
1508                                       BN_get0_nist_prime_192())))
1509             goto err;
1510     }
1511
1512     /* Passes because this is a valid curve */
1513     if (!TEST_int_eq(EC_GROUP_check_named_curve(group, 0, NULL), nid)
1514         /* Only NIST curves pass */
1515         || !TEST_int_eq(EC_GROUP_check_named_curve(group, 1, NULL),
1516                         EC_curve_nid2nist(nid) != NULL ? nid : NID_undef))
1517         goto err;
1518
1519     /* Fail if the curve name doesn't match the parameters */
1520     EC_GROUP_set_curve_name(group, nid + 1);
1521     ERR_set_mark();
1522     if (!TEST_int_le(EC_GROUP_check_named_curve(group, 0, NULL), 0))
1523         goto err;
1524     ERR_pop_to_mark();
1525
1526     /* Restore curve name and ensure it's passing */
1527     EC_GROUP_set_curve_name(group, nid);
1528     if (!TEST_int_eq(EC_GROUP_check_named_curve(group, 0, NULL), nid))
1529         goto err;
1530
1531     if (!TEST_int_eq(EC_GROUP_set_seed(group, invalid_seed, invalid_seed_len),
1532                      invalid_seed_len))
1533         goto err;
1534
1535     if (has_seed) {
1536         /*
1537          * If the built-in curve has a seed and we set the seed to another value
1538          * then it will fail the check.
1539          */
1540         if (!TEST_int_eq(EC_GROUP_check_named_curve(group, 0, NULL), 0))
1541             goto err;
1542     } else {
1543         /*
1544          * If the built-in curve does not have a seed then setting the seed will
1545          * pass the check (as the seed is optional).
1546          */
1547         if (!TEST_int_eq(EC_GROUP_check_named_curve(group, 0, NULL), nid))
1548             goto err;
1549     }
1550     /* Pass if the seed is unknown (as it is optional) */
1551     if (!TEST_int_eq(EC_GROUP_set_seed(group, NULL, 0), 1)
1552         || !TEST_int_eq(EC_GROUP_check_named_curve(group, 0, NULL), nid))
1553         goto err;
1554
1555     /* Check that a duped group passes */
1556     if (!TEST_int_eq(EC_GROUP_check_named_curve(gtest, 0, NULL), nid))
1557         goto err;
1558
1559     /* check that changing any generator parameter fails */
1560     if (!TEST_true(EC_GROUP_set_generator(gtest, other_gen, group_order,
1561                                           group_cofactor))
1562         || !TEST_int_eq(EC_GROUP_check_named_curve(gtest, 0, NULL), 0)
1563         || !TEST_true(EC_GROUP_set_generator(gtest, group_gen, other_order,
1564                                              group_cofactor))
1565         || !TEST_int_eq(EC_GROUP_check_named_curve(gtest, 0, NULL), 0)
1566         /* The order is not an optional field, so this should fail */
1567         || !TEST_false(EC_GROUP_set_generator(gtest, group_gen, NULL,
1568                                               group_cofactor))
1569         || !TEST_true(EC_GROUP_set_generator(gtest, group_gen, group_order,
1570                                              other_cofactor))
1571         || !TEST_int_eq(EC_GROUP_check_named_curve(gtest, 0, NULL), 0)
1572         /* Check that if the cofactor is not set then it still passes */
1573         || !TEST_true(EC_GROUP_set_generator(gtest, group_gen, group_order,
1574                                              NULL))
1575         || !TEST_int_eq(EC_GROUP_check_named_curve(gtest, 0, NULL), nid)
1576         /* check that restoring the generator passes */
1577         || !TEST_true(EC_GROUP_set_generator(gtest, group_gen, group_order,
1578                                              group_cofactor))
1579         || !TEST_int_eq(EC_GROUP_check_named_curve(gtest, 0, NULL), nid))
1580         goto err;
1581
1582     /*
1583      * check that changing any curve parameter fails
1584      *
1585      * Setting arbitrary p, a or b might fail for some EC_GROUPs
1586      * depending on the internal EC_METHOD implementation, hence run
1587      * these tests conditionally to the success of EC_GROUP_set_curve().
1588      */
1589     ERR_set_mark();
1590     if (EC_GROUP_set_curve(gtest, other_p, group_a, group_b, NULL)) {
1591         if (!TEST_int_le(EC_GROUP_check_named_curve(gtest, 0, NULL), 0))
1592             goto err;
1593     } else {
1594         /* clear the error stack if EC_GROUP_set_curve() failed */
1595         ERR_pop_to_mark();
1596         ERR_set_mark();
1597     }
1598     if (EC_GROUP_set_curve(gtest, group_p, other_a, group_b, NULL)) {
1599         if (!TEST_int_le(EC_GROUP_check_named_curve(gtest, 0, NULL), 0))
1600             goto err;
1601     } else {
1602         /* clear the error stack if EC_GROUP_set_curve() failed */
1603         ERR_pop_to_mark();
1604         ERR_set_mark();
1605     }
1606     if (EC_GROUP_set_curve(gtest, group_p, group_a, other_b, NULL)) {
1607         if (!TEST_int_le(EC_GROUP_check_named_curve(gtest, 0, NULL), 0))
1608             goto err;
1609     } else {
1610         /* clear the error stack if EC_GROUP_set_curve() failed */
1611         ERR_pop_to_mark();
1612         ERR_set_mark();
1613     }
1614     ERR_pop_to_mark();
1615
1616     /* Check that restoring the curve parameters passes */
1617     if (!TEST_true(EC_GROUP_set_curve(gtest, group_p, group_a, group_b, NULL))
1618         || !TEST_int_eq(EC_GROUP_check_named_curve(gtest, 0, NULL), nid))
1619         goto err;
1620
1621     ret = 1;
1622 err:
1623     BN_free(group_p);
1624     BN_free(other_p);
1625     BN_free(group_a);
1626     BN_free(other_a);
1627     BN_free(group_b);
1628     BN_free(other_b);
1629     BN_free(group_cofactor);
1630     BN_free(other_cofactor);
1631     BN_free(other_order);
1632     EC_POINT_free(other_gen);
1633     EC_GROUP_free(gtest);
1634     EC_GROUP_free(group);
1635     BN_CTX_free(bn_ctx);
1636     return ret;
1637 }
1638
1639 /*
1640  * This checks the lookup capability of EC_GROUP_check_named_curve()
1641  * when the given group was created with explicit parameters.
1642  *
1643  * It is possible to retrieve an alternative alias that does not match
1644  * the original nid in this case.
1645  */
1646 static int check_named_curve_lookup_test(int id)
1647 {
1648     int ret = 0, nid, rv = 0;
1649     EC_GROUP *g = NULL , *ga = NULL;
1650     ECPARAMETERS *p = NULL, *pa = NULL;
1651     BN_CTX *ctx = NULL;
1652
1653     /* Do some setup */
1654     nid = curves[id].nid;
1655     if (!TEST_ptr(ctx = BN_CTX_new())
1656         || !TEST_ptr(g = EC_GROUP_new_by_curve_name(nid))
1657         || !TEST_ptr(p = EC_GROUP_get_ecparameters(g, NULL)))
1658         goto err;
1659
1660     /* replace with group from explicit parameters */
1661     EC_GROUP_free(g);
1662     if (!TEST_ptr(g = EC_GROUP_new_from_ecparameters(p)))
1663         goto err;
1664
1665     if (!TEST_int_gt(rv = EC_GROUP_check_named_curve(g, 0, NULL), 0))
1666         goto err;
1667     if (rv != nid) {
1668         /*
1669          * Found an alias:
1670          * fail if the returned nid is not an alias of the original group.
1671          *
1672          * The comparison here is done by comparing two explicit
1673          * parameter EC_GROUPs with EC_GROUP_cmp(), to ensure the
1674          * comparison happens with unnamed EC_GROUPs using the same
1675          * EC_METHODs.
1676          */
1677         if (!TEST_ptr(ga = EC_GROUP_new_by_curve_name(rv))
1678                 || !TEST_ptr(pa = EC_GROUP_get_ecparameters(ga, NULL)))
1679             goto err;
1680
1681         /* replace with group from explicit parameters, then compare */
1682         EC_GROUP_free(ga);
1683         if (!TEST_ptr(ga = EC_GROUP_new_from_ecparameters(pa))
1684                 || !TEST_int_eq(EC_GROUP_cmp(g, ga, ctx), 0))
1685             goto err;
1686     }
1687
1688     ret = 1;
1689
1690  err:
1691     EC_GROUP_free(g);
1692     EC_GROUP_free(ga);
1693     ECPARAMETERS_free(p);
1694     ECPARAMETERS_free(pa);
1695     BN_CTX_free(ctx);
1696
1697     return ret;
1698 }
1699
1700 /*
1701  * Sometime we cannot compare nids for equality, as the built-in curve table
1702  * includes aliases with different names for the same curve.
1703  *
1704  * This function returns TRUE (1) if the checked nids are identical, or if they
1705  * alias to the same curve. FALSE (0) otherwise.
1706  */
1707 static ossl_inline
1708 int are_ec_nids_compatible(int n1d, int n2d)
1709 {
1710     int ret = 0;
1711     switch (n1d) {
1712 # ifndef OPENSSL_NO_EC2M
1713         case NID_sect113r1:
1714         case NID_wap_wsg_idm_ecid_wtls4:
1715             ret = (n2d == NID_sect113r1 || n2d == NID_wap_wsg_idm_ecid_wtls4);
1716             break;
1717         case NID_sect163k1:
1718         case NID_wap_wsg_idm_ecid_wtls3:
1719             ret = (n2d == NID_sect163k1 || n2d == NID_wap_wsg_idm_ecid_wtls3);
1720             break;
1721         case NID_sect233k1:
1722         case NID_wap_wsg_idm_ecid_wtls10:
1723             ret = (n2d == NID_sect233k1 || n2d == NID_wap_wsg_idm_ecid_wtls10);
1724             break;
1725         case NID_sect233r1:
1726         case NID_wap_wsg_idm_ecid_wtls11:
1727             ret = (n2d == NID_sect233r1 || n2d == NID_wap_wsg_idm_ecid_wtls11);
1728             break;
1729         case NID_X9_62_c2pnb163v1:
1730         case NID_wap_wsg_idm_ecid_wtls5:
1731             ret = (n2d == NID_X9_62_c2pnb163v1
1732                    || n2d == NID_wap_wsg_idm_ecid_wtls5);
1733             break;
1734 # endif /* OPENSSL_NO_EC2M */
1735         case NID_secp112r1:
1736         case NID_wap_wsg_idm_ecid_wtls6:
1737             ret = (n2d == NID_secp112r1 || n2d == NID_wap_wsg_idm_ecid_wtls6);
1738             break;
1739         case NID_secp160r2:
1740         case NID_wap_wsg_idm_ecid_wtls7:
1741             ret = (n2d == NID_secp160r2 || n2d == NID_wap_wsg_idm_ecid_wtls7);
1742             break;
1743 # ifdef OPENSSL_NO_EC_NISTP_64_GCC_128
1744         case NID_secp224r1:
1745         case NID_wap_wsg_idm_ecid_wtls12:
1746             ret = (n2d == NID_secp224r1 || n2d == NID_wap_wsg_idm_ecid_wtls12);
1747             break;
1748 # else
1749         /*
1750          * For SEC P-224 we want to ensure that the SECP nid is returned, as
1751          * that is associated with a specialized method.
1752          */
1753         case NID_wap_wsg_idm_ecid_wtls12:
1754             ret = (n2d == NID_secp224r1);
1755             break;
1756 # endif /* def(OPENSSL_NO_EC_NISTP_64_GCC_128) */
1757
1758         default:
1759             ret = (n1d == n2d);
1760     }
1761     return ret;
1762 }
1763
1764 /*
1765  * This checks that EC_GROUP_bew_from_ecparameters() returns a "named"
1766  * EC_GROUP for built-in curves.
1767  *
1768  * Note that it is possible to retrieve an alternative alias that does not match
1769  * the original nid.
1770  *
1771  * Ensure that the OPENSSL_EC_EXPLICIT_CURVE ASN1 flag is set.
1772  */
1773 static int check_named_curve_from_ecparameters(int id)
1774 {
1775     int ret = 0, nid, tnid;
1776     EC_GROUP *group = NULL, *tgroup = NULL, *tmpg = NULL;
1777     const EC_POINT *group_gen = NULL;
1778     EC_POINT *other_gen = NULL;
1779     BIGNUM *group_cofactor = NULL, *other_cofactor = NULL;
1780     BIGNUM *other_gen_x = NULL, *other_gen_y = NULL;
1781     const BIGNUM *group_order = NULL;
1782     BIGNUM *other_order = NULL;
1783     BN_CTX *bn_ctx = NULL;
1784     static const unsigned char invalid_seed[] = "THIS IS NOT A VALID SEED";
1785     static size_t invalid_seed_len = sizeof(invalid_seed);
1786     ECPARAMETERS *params = NULL, *other_params = NULL;
1787     EC_GROUP *g_ary[8] = {NULL};
1788     EC_GROUP **g_next = &g_ary[0];
1789     ECPARAMETERS *p_ary[8] = {NULL};
1790     ECPARAMETERS **p_next = &p_ary[0];
1791
1792     /* Do some setup */
1793     nid = curves[id].nid;
1794     TEST_note("Curve %s", OBJ_nid2sn(nid));
1795     if (!TEST_ptr(bn_ctx = BN_CTX_new()))
1796         return ret;
1797     BN_CTX_start(bn_ctx);
1798
1799     if (/* Allocations */
1800         !TEST_ptr(group_cofactor = BN_CTX_get(bn_ctx))
1801         || !TEST_ptr(other_gen_x = BN_CTX_get(bn_ctx))
1802         || !TEST_ptr(other_gen_y = BN_CTX_get(bn_ctx))
1803         || !TEST_ptr(other_order = BN_CTX_get(bn_ctx))
1804         || !TEST_ptr(other_cofactor = BN_CTX_get(bn_ctx))
1805         /* Generate reference group and params */
1806         || !TEST_ptr(group = EC_GROUP_new_by_curve_name(nid))
1807         || !TEST_ptr(params = EC_GROUP_get_ecparameters(group, NULL))
1808         || !TEST_ptr(group_gen = EC_GROUP_get0_generator(group))
1809         || !TEST_ptr(group_order = EC_GROUP_get0_order(group))
1810         || !TEST_true(EC_GROUP_get_cofactor(group, group_cofactor, NULL))
1811         /* compute `other_*` values */
1812         || !TEST_ptr(tmpg = EC_GROUP_dup(group))
1813         || !TEST_ptr(other_gen = EC_POINT_dup(group_gen, group))
1814         || !TEST_true(EC_POINT_add(group, other_gen, group_gen, group_gen, NULL))
1815         || !TEST_true(EC_POINT_get_affine_coordinates(group, other_gen,
1816                       other_gen_x, other_gen_y, bn_ctx))
1817         || !TEST_true(BN_copy(other_order, group_order))
1818         || !TEST_true(BN_add_word(other_order, 1))
1819         || !TEST_true(BN_copy(other_cofactor, group_cofactor))
1820         || !TEST_true(BN_add_word(other_cofactor, 1)))
1821         goto err;
1822
1823     EC_POINT_free(other_gen);
1824     other_gen = NULL;
1825
1826     if (!TEST_ptr(other_gen = EC_POINT_new(tmpg))
1827         || !TEST_true(EC_POINT_set_affine_coordinates(tmpg, other_gen,
1828                                                       other_gen_x, other_gen_y,
1829                                                       bn_ctx)))
1830         goto err;
1831
1832     /*
1833      * ###########################
1834      * # Actual tests start here #
1835      * ###########################
1836      */
1837
1838     /*
1839      * Creating a group from built-in explicit parameters returns a
1840      * "named" EC_GROUP
1841      */
1842     if (!TEST_ptr(tgroup = *g_next++ = EC_GROUP_new_from_ecparameters(params))
1843         || !TEST_int_ne((tnid = EC_GROUP_get_curve_name(tgroup)), NID_undef))
1844         goto err;
1845     /*
1846      * We cannot always guarantee the names match, as the built-in table
1847      * contains aliases for the same curve with different names.
1848      */
1849     if (!TEST_true(are_ec_nids_compatible(nid, tnid))) {
1850         TEST_info("nid = %s, tnid = %s", OBJ_nid2sn(nid), OBJ_nid2sn(tnid));
1851         goto err;
1852     }
1853     /* Ensure that the OPENSSL_EC_EXPLICIT_CURVE ASN1 flag is set. */
1854     if (!TEST_int_eq(EC_GROUP_get_asn1_flag(tgroup), OPENSSL_EC_EXPLICIT_CURVE))
1855         goto err;
1856
1857     /*
1858      * An invalid seed in the parameters should be ignored: expect a "named"
1859      * group.
1860      */
1861     if (!TEST_int_eq(EC_GROUP_set_seed(tmpg, invalid_seed, invalid_seed_len),
1862                      invalid_seed_len)
1863             || !TEST_ptr(other_params = *p_next++ =
1864                          EC_GROUP_get_ecparameters(tmpg, NULL))
1865             || !TEST_ptr(tgroup = *g_next++ =
1866                           EC_GROUP_new_from_ecparameters(other_params))
1867             || !TEST_int_ne((tnid = EC_GROUP_get_curve_name(tgroup)), NID_undef)
1868             || !TEST_true(are_ec_nids_compatible(nid, tnid))
1869             || !TEST_int_eq(EC_GROUP_get_asn1_flag(tgroup),
1870                             OPENSSL_EC_EXPLICIT_CURVE)) {
1871         TEST_info("nid = %s, tnid = %s", OBJ_nid2sn(nid), OBJ_nid2sn(tnid));
1872         goto err;
1873     }
1874
1875     /*
1876      * A null seed in the parameters should be ignored, as it is optional:
1877      * expect a "named" group.
1878      */
1879     if (!TEST_int_eq(EC_GROUP_set_seed(tmpg, NULL, 0), 1)
1880             || !TEST_ptr(other_params = *p_next++ =
1881                          EC_GROUP_get_ecparameters(tmpg, NULL))
1882             || !TEST_ptr(tgroup = *g_next++ =
1883                           EC_GROUP_new_from_ecparameters(other_params))
1884             || !TEST_int_ne((tnid = EC_GROUP_get_curve_name(tgroup)), NID_undef)
1885             || !TEST_true(are_ec_nids_compatible(nid, tnid))
1886             || !TEST_int_eq(EC_GROUP_get_asn1_flag(tgroup),
1887                             OPENSSL_EC_EXPLICIT_CURVE)) {
1888         TEST_info("nid = %s, tnid = %s", OBJ_nid2sn(nid), OBJ_nid2sn(tnid));
1889         goto err;
1890     }
1891
1892     /*
1893      * Check that changing any of the generator parameters does not yield a
1894      * match with the built-in curves
1895      */
1896     if (/* Other gen, same group order & cofactor */
1897         !TEST_true(EC_GROUP_set_generator(tmpg, other_gen, group_order,
1898                                           group_cofactor))
1899         || !TEST_ptr(other_params = *p_next++ =
1900                      EC_GROUP_get_ecparameters(tmpg, NULL))
1901         || !TEST_ptr(tgroup = *g_next++ =
1902                       EC_GROUP_new_from_ecparameters(other_params))
1903         || !TEST_int_eq((tnid = EC_GROUP_get_curve_name(tgroup)), NID_undef)
1904         /* Same gen & cofactor, different order */
1905         || !TEST_true(EC_GROUP_set_generator(tmpg, group_gen, other_order,
1906                                              group_cofactor))
1907         || !TEST_ptr(other_params = *p_next++ =
1908                      EC_GROUP_get_ecparameters(tmpg, NULL))
1909         || !TEST_ptr(tgroup = *g_next++ =
1910                       EC_GROUP_new_from_ecparameters(other_params))
1911         || !TEST_int_eq((tnid = EC_GROUP_get_curve_name(tgroup)), NID_undef)
1912         /* The order is not an optional field, so this should fail */
1913         || !TEST_false(EC_GROUP_set_generator(tmpg, group_gen, NULL,
1914                                               group_cofactor))
1915         /* Check that a wrong cofactor is ignored, and we still match */
1916         || !TEST_true(EC_GROUP_set_generator(tmpg, group_gen, group_order,
1917                                              other_cofactor))
1918         || !TEST_ptr(other_params = *p_next++ =
1919                      EC_GROUP_get_ecparameters(tmpg, NULL))
1920         || !TEST_ptr(tgroup = *g_next++ =
1921                       EC_GROUP_new_from_ecparameters(other_params))
1922         || !TEST_int_ne((tnid = EC_GROUP_get_curve_name(tgroup)), NID_undef)
1923         || !TEST_true(are_ec_nids_compatible(nid, tnid))
1924         || !TEST_int_eq(EC_GROUP_get_asn1_flag(tgroup),
1925                         OPENSSL_EC_EXPLICIT_CURVE)
1926         /* Check that if the cofactor is not set then it still matches */
1927         || !TEST_true(EC_GROUP_set_generator(tmpg, group_gen, group_order,
1928                                              NULL))
1929         || !TEST_ptr(other_params = *p_next++ =
1930                      EC_GROUP_get_ecparameters(tmpg, NULL))
1931         || !TEST_ptr(tgroup = *g_next++ =
1932                       EC_GROUP_new_from_ecparameters(other_params))
1933         || !TEST_int_ne((tnid = EC_GROUP_get_curve_name(tgroup)), NID_undef)
1934         || !TEST_true(are_ec_nids_compatible(nid, tnid))
1935         || !TEST_int_eq(EC_GROUP_get_asn1_flag(tgroup),
1936                         OPENSSL_EC_EXPLICIT_CURVE)
1937         /* check that restoring the generator passes */
1938         || !TEST_true(EC_GROUP_set_generator(tmpg, group_gen, group_order,
1939                                              group_cofactor))
1940         || !TEST_ptr(other_params = *p_next++ =
1941                      EC_GROUP_get_ecparameters(tmpg, NULL))
1942         || !TEST_ptr(tgroup = *g_next++ =
1943                       EC_GROUP_new_from_ecparameters(other_params))
1944         || !TEST_int_ne((tnid = EC_GROUP_get_curve_name(tgroup)), NID_undef)
1945         || !TEST_true(are_ec_nids_compatible(nid, tnid))
1946         || !TEST_int_eq(EC_GROUP_get_asn1_flag(tgroup),
1947                         OPENSSL_EC_EXPLICIT_CURVE))
1948         goto err;
1949
1950     ret = 1;
1951 err:
1952     for (g_next = &g_ary[0]; g_next < g_ary + OSSL_NELEM(g_ary); g_next++)
1953         EC_GROUP_free(*g_next);
1954     for (p_next = &p_ary[0]; p_next < p_ary + OSSL_NELEM(g_ary); p_next++)
1955         ECPARAMETERS_free(*p_next);
1956     ECPARAMETERS_free(params);
1957     EC_POINT_free(other_gen);
1958     EC_GROUP_free(tmpg);
1959     EC_GROUP_free(group);
1960     BN_CTX_end(bn_ctx);
1961     BN_CTX_free(bn_ctx);
1962     return ret;
1963 }
1964
1965
1966 static int parameter_test(void)
1967 {
1968     EC_GROUP *group = NULL, *group2 = NULL;
1969     ECPARAMETERS *ecparameters = NULL;
1970     unsigned char *buf = NULL;
1971     int r = 0, len;
1972
1973     if (!TEST_ptr(group = EC_GROUP_new_by_curve_name(NID_secp384r1))
1974         || !TEST_ptr(ecparameters = EC_GROUP_get_ecparameters(group, NULL))
1975         || !TEST_ptr(group2 = EC_GROUP_new_from_ecparameters(ecparameters))
1976         || !TEST_int_eq(EC_GROUP_cmp(group, group2, NULL), 0))
1977         goto err;
1978
1979     EC_GROUP_free(group);
1980     group = NULL;
1981
1982     /* Test the named curve encoding, which should be default. */
1983     if (!TEST_ptr(group = EC_GROUP_new_by_curve_name(NID_secp521r1))
1984         || !TEST_true((len = i2d_ECPKParameters(group, &buf)) >= 0)
1985         || !TEST_mem_eq(buf, len, p521_named, sizeof(p521_named)))
1986         goto err;
1987
1988     OPENSSL_free(buf);
1989     buf = NULL;
1990
1991     /*
1992      * Test the explicit encoding. P-521 requires correctly zero-padding the
1993      * curve coefficients.
1994      */
1995     EC_GROUP_set_asn1_flag(group, OPENSSL_EC_EXPLICIT_CURVE);
1996     if (!TEST_true((len = i2d_ECPKParameters(group, &buf)) >= 0)
1997         || !TEST_mem_eq(buf, len, p521_explicit, sizeof(p521_explicit)))
1998         goto err;
1999
2000     r = 1;
2001 err:
2002     EC_GROUP_free(group);
2003     EC_GROUP_free(group2);
2004     ECPARAMETERS_free(ecparameters);
2005     OPENSSL_free(buf);
2006     return r;
2007 }
2008
2009 /*-
2010  * random 256-bit explicit parameters curve, cofactor absent
2011  * order:    0x0c38d96a9f892b88772ec2e39614a82f4f (132 bit)
2012  * cofactor:   0x12bc94785251297abfafddf1565100da (125 bit)
2013  */
2014 static const unsigned char params_cf_pass[] = {
2015     0x30, 0x81, 0xcd, 0x02, 0x01, 0x01, 0x30, 0x2c, 0x06, 0x07, 0x2a, 0x86,
2016     0x48, 0xce, 0x3d, 0x01, 0x01, 0x02, 0x21, 0x00, 0xe5, 0x00, 0x1f, 0xc5,
2017     0xca, 0x71, 0x9d, 0x8e, 0xf7, 0x07, 0x4b, 0x48, 0x37, 0xf9, 0x33, 0x2d,
2018     0x71, 0xbf, 0x79, 0xe7, 0xdc, 0x91, 0xc2, 0xff, 0xb6, 0x7b, 0xc3, 0x93,
2019     0x44, 0x88, 0xe6, 0x91, 0x30, 0x44, 0x04, 0x20, 0xe5, 0x00, 0x1f, 0xc5,
2020     0xca, 0x71, 0x9d, 0x8e, 0xf7, 0x07, 0x4b, 0x48, 0x37, 0xf9, 0x33, 0x2d,
2021     0x71, 0xbf, 0x79, 0xe7, 0xdc, 0x91, 0xc2, 0xff, 0xb6, 0x7b, 0xc3, 0x93,
2022     0x44, 0x88, 0xe6, 0x8e, 0x04, 0x20, 0x18, 0x8c, 0x59, 0x57, 0xc4, 0xbc,
2023     0x85, 0x57, 0xc3, 0x66, 0x9f, 0x89, 0xd5, 0x92, 0x0d, 0x7e, 0x42, 0x27,
2024     0x07, 0x64, 0xaa, 0x26, 0xed, 0x89, 0xc4, 0x09, 0x05, 0x4d, 0xc7, 0x23,
2025     0x47, 0xda, 0x04, 0x41, 0x04, 0x1b, 0x6b, 0x41, 0x0b, 0xf9, 0xfb, 0x77,
2026     0xfd, 0x50, 0xb7, 0x3e, 0x23, 0xa3, 0xec, 0x9a, 0x3b, 0x09, 0x31, 0x6b,
2027     0xfa, 0xf6, 0xce, 0x1f, 0xff, 0xeb, 0x57, 0x93, 0x24, 0x70, 0xf3, 0xf4,
2028     0xba, 0x7e, 0xfa, 0x86, 0x6e, 0x19, 0x89, 0xe3, 0x55, 0x6d, 0x5a, 0xe9,
2029     0xc0, 0x3d, 0xbc, 0xfb, 0xaf, 0xad, 0xd4, 0x7e, 0xa6, 0xe5, 0xfa, 0x1a,
2030     0x58, 0x07, 0x9e, 0x8f, 0x0d, 0x3b, 0xf7, 0x38, 0xca, 0x02, 0x11, 0x0c,
2031     0x38, 0xd9, 0x6a, 0x9f, 0x89, 0x2b, 0x88, 0x77, 0x2e, 0xc2, 0xe3, 0x96,
2032     0x14, 0xa8, 0x2f, 0x4f
2033 };
2034
2035 /*-
2036  * random 256-bit explicit parameters curve, cofactor absent
2037  * order:    0x045a75c0c17228ebd9b169a10e34a22101 (131 bit)
2038  * cofactor:   0x2e134b4ede82649f67a2e559d361e5fe (126 bit)
2039  */
2040 static const unsigned char params_cf_fail[] = {
2041     0x30, 0x81, 0xcd, 0x02, 0x01, 0x01, 0x30, 0x2c, 0x06, 0x07, 0x2a, 0x86,
2042     0x48, 0xce, 0x3d, 0x01, 0x01, 0x02, 0x21, 0x00, 0xc8, 0x95, 0x27, 0x37,
2043     0xe8, 0xe1, 0xfd, 0xcc, 0xf9, 0x6e, 0x0c, 0xa6, 0x21, 0xc1, 0x7d, 0x6b,
2044     0x9d, 0x44, 0x42, 0xea, 0x73, 0x4e, 0x04, 0xb6, 0xac, 0x62, 0x50, 0xd0,
2045     0x33, 0xc2, 0xea, 0x13, 0x30, 0x44, 0x04, 0x20, 0xc8, 0x95, 0x27, 0x37,
2046     0xe8, 0xe1, 0xfd, 0xcc, 0xf9, 0x6e, 0x0c, 0xa6, 0x21, 0xc1, 0x7d, 0x6b,
2047     0x9d, 0x44, 0x42, 0xea, 0x73, 0x4e, 0x04, 0xb6, 0xac, 0x62, 0x50, 0xd0,
2048     0x33, 0xc2, 0xea, 0x10, 0x04, 0x20, 0xbf, 0xa6, 0xa8, 0x05, 0x1d, 0x09,
2049     0xac, 0x70, 0x39, 0xbb, 0x4d, 0xb2, 0x90, 0x8a, 0x15, 0x41, 0x14, 0x1d,
2050     0x11, 0x86, 0x9f, 0x13, 0xa2, 0x63, 0x1a, 0xda, 0x95, 0x22, 0x4d, 0x02,
2051     0x15, 0x0a, 0x04, 0x41, 0x04, 0xaf, 0x16, 0x71, 0xf9, 0xc4, 0xc8, 0x59,
2052     0x1d, 0xa3, 0x6f, 0xe7, 0xc3, 0x57, 0xa1, 0xfa, 0x9f, 0x49, 0x7c, 0x11,
2053     0x27, 0x05, 0xa0, 0x7f, 0xff, 0xf9, 0xe0, 0xe7, 0x92, 0xdd, 0x9c, 0x24,
2054     0x8e, 0xc7, 0xb9, 0x52, 0x71, 0x3f, 0xbc, 0x7f, 0x6a, 0x9f, 0x35, 0x70,
2055     0xe1, 0x27, 0xd5, 0x35, 0x8a, 0x13, 0xfa, 0xa8, 0x33, 0x3e, 0xd4, 0x73,
2056     0x1c, 0x14, 0x58, 0x9e, 0xc7, 0x0a, 0x87, 0x65, 0x8d, 0x02, 0x11, 0x04,
2057     0x5a, 0x75, 0xc0, 0xc1, 0x72, 0x28, 0xeb, 0xd9, 0xb1, 0x69, 0xa1, 0x0e,
2058     0x34, 0xa2, 0x21, 0x01
2059 };
2060
2061 /*-
2062  * Test two random 256-bit explicit parameters curves with absent cofactor.
2063  * The two curves are chosen to roughly straddle the bounds at which the lib
2064  * can compute the cofactor automatically, roughly 4*sqrt(p). So test that:
2065  *
2066  * - params_cf_pass: order is sufficiently close to p to compute cofactor
2067  * - params_cf_fail: order is too far away from p to compute cofactor
2068  *
2069  * For standards-compliant curves, cofactor is chosen as small as possible.
2070  * So you can see neither of these curves are fit for cryptographic use.
2071  *
2072  * Some standards even mandate an upper bound on the cofactor, e.g. SECG1 v2:
2073  * h <= 2**(t/8) where t is the security level of the curve, for which the lib
2074  * will always succeed in computing the cofactor. Neither of these curves
2075  * conform to that -- this is just robustness testing.
2076  */
2077 static int cofactor_range_test(void)
2078 {
2079     EC_GROUP *group = NULL;
2080     BIGNUM *cf = NULL;
2081     int ret = 0;
2082     const unsigned char *b1 = (const unsigned char *)params_cf_fail;
2083     const unsigned char *b2 = (const unsigned char *)params_cf_pass;
2084
2085     if (!TEST_ptr(group = d2i_ECPKParameters(NULL, &b1, sizeof(params_cf_fail)))
2086         || !TEST_BN_eq_zero(EC_GROUP_get0_cofactor(group))
2087         || !TEST_ptr(group = d2i_ECPKParameters(&group, &b2,
2088                                                 sizeof(params_cf_pass)))
2089         || !TEST_int_gt(BN_hex2bn(&cf, "12bc94785251297abfafddf1565100da"), 0)
2090         || !TEST_BN_eq(cf, EC_GROUP_get0_cofactor(group)))
2091         goto err;
2092     ret = 1;
2093  err:
2094     BN_free(cf);
2095     EC_GROUP_free(group);
2096     return ret;
2097 }
2098
2099 /*-
2100  * For named curves, test that:
2101  * - the lib correctly computes the cofactor if passed a NULL or zero cofactor
2102  * - a nonsensical cofactor throws an error (negative test)
2103  * - nonsensical orders throw errors (negative tests)
2104  */
2105 static int cardinality_test(int n)
2106 {
2107     int ret = 0, is_binary = 0;
2108     int nid = curves[n].nid;
2109     BN_CTX *ctx = NULL;
2110     EC_GROUP *g1 = NULL, *g2 = NULL;
2111     EC_POINT *g2_gen = NULL;
2112     BIGNUM *g1_p = NULL, *g1_a = NULL, *g1_b = NULL, *g1_x = NULL, *g1_y = NULL,
2113            *g1_order = NULL, *g1_cf = NULL, *g2_cf = NULL;
2114
2115     TEST_info("Curve %s cardinality test", OBJ_nid2sn(nid));
2116
2117     if (!TEST_ptr(ctx = BN_CTX_new())
2118         || !TEST_ptr(g1 = EC_GROUP_new_by_curve_name(nid))) {
2119         BN_CTX_free(ctx);
2120         return 0;
2121     }
2122
2123     is_binary = (EC_GROUP_get_field_type(g1) == NID_X9_62_characteristic_two_field);
2124
2125     BN_CTX_start(ctx);
2126     g1_p = BN_CTX_get(ctx);
2127     g1_a = BN_CTX_get(ctx);
2128     g1_b = BN_CTX_get(ctx);
2129     g1_x = BN_CTX_get(ctx);
2130     g1_y = BN_CTX_get(ctx);
2131     g1_order = BN_CTX_get(ctx);
2132     g1_cf = BN_CTX_get(ctx);
2133
2134     if (!TEST_ptr(g2_cf = BN_CTX_get(ctx))
2135         /* pull out the explicit curve parameters */
2136         || !TEST_true(EC_GROUP_get_curve(g1, g1_p, g1_a, g1_b, ctx))
2137         || !TEST_true(EC_POINT_get_affine_coordinates(g1,
2138                       EC_GROUP_get0_generator(g1), g1_x, g1_y, ctx))
2139         || !TEST_true(BN_copy(g1_order, EC_GROUP_get0_order(g1)))
2140         || !TEST_true(EC_GROUP_get_cofactor(g1, g1_cf, ctx))
2141         /* construct g2 manually with g1 parameters */
2142 # ifndef OPENSSL_NO_EC2M
2143         || !TEST_ptr(g2 = (is_binary) ?
2144                            EC_GROUP_new_curve_GF2m(g1_p, g1_a, g1_b, ctx) :
2145                            EC_GROUP_new_curve_GFp(g1_p, g1_a, g1_b, ctx))
2146 # else
2147         || !TEST_int_eq(0, is_binary)
2148         || !TEST_ptr(g2 = EC_GROUP_new_curve_GFp(g1_p, g1_a, g1_b, ctx))
2149 # endif
2150         || !TEST_ptr(g2_gen = EC_POINT_new(g2))
2151         || !TEST_true(EC_POINT_set_affine_coordinates(g2, g2_gen, g1_x, g1_y, ctx))
2152         /* pass NULL cofactor: lib should compute it */
2153         || !TEST_true(EC_GROUP_set_generator(g2, g2_gen, g1_order, NULL))
2154         || !TEST_true(EC_GROUP_get_cofactor(g2, g2_cf, ctx))
2155         || !TEST_BN_eq(g1_cf, g2_cf)
2156         /* pass zero cofactor: lib should compute it */
2157         || !TEST_true(BN_set_word(g2_cf, 0))
2158         || !TEST_true(EC_GROUP_set_generator(g2, g2_gen, g1_order, g2_cf))
2159         || !TEST_true(EC_GROUP_get_cofactor(g2, g2_cf, ctx))
2160         || !TEST_BN_eq(g1_cf, g2_cf)
2161         /* negative test for invalid cofactor */
2162         || !TEST_true(BN_set_word(g2_cf, 0))
2163         || !TEST_true(BN_sub(g2_cf, g2_cf, BN_value_one()))
2164         || !TEST_false(EC_GROUP_set_generator(g2, g2_gen, g1_order, g2_cf))
2165         /* negative test for NULL order */
2166         || !TEST_false(EC_GROUP_set_generator(g2, g2_gen, NULL, NULL))
2167         /* negative test for zero order */
2168         || !TEST_true(BN_set_word(g1_order, 0))
2169         || !TEST_false(EC_GROUP_set_generator(g2, g2_gen, g1_order, NULL))
2170         /* negative test for negative order */
2171         || !TEST_true(BN_set_word(g2_cf, 0))
2172         || !TEST_true(BN_sub(g2_cf, g2_cf, BN_value_one()))
2173         || !TEST_false(EC_GROUP_set_generator(g2, g2_gen, g1_order, NULL))
2174         /* negative test for too large order */
2175         || !TEST_true(BN_lshift(g1_order, g1_p, 2))
2176         || !TEST_false(EC_GROUP_set_generator(g2, g2_gen, g1_order, NULL)))
2177         goto err;
2178     ret = 1;
2179  err:
2180     EC_POINT_free(g2_gen);
2181     EC_GROUP_free(g1);
2182     EC_GROUP_free(g2);
2183     BN_CTX_end(ctx);
2184     BN_CTX_free(ctx);
2185     return ret;
2186 }
2187
2188 static int check_ec_key_field_public_range_test(int id)
2189 {
2190     int ret = 0, type = 0;
2191     const EC_POINT *pub = NULL;
2192     const EC_GROUP *group = NULL;
2193     const BIGNUM *field = NULL;
2194     BIGNUM *x = NULL, *y = NULL;
2195     EC_KEY *key = NULL;
2196
2197     if (!TEST_ptr(x = BN_new())
2198             || !TEST_ptr(y = BN_new())
2199             || !TEST_ptr(key = EC_KEY_new_by_curve_name(curves[id].nid))
2200             || !TEST_ptr(group = EC_KEY_get0_group(key))
2201             || !TEST_ptr(field = EC_GROUP_get0_field(group))
2202             || !TEST_int_gt(EC_KEY_generate_key(key), 0)
2203             || !TEST_int_gt(EC_KEY_check_key(key), 0)
2204             || !TEST_ptr(pub = EC_KEY_get0_public_key(key))
2205             || !TEST_int_gt(EC_POINT_get_affine_coordinates(group, pub, x, y,
2206                                                             NULL), 0))
2207         goto err;
2208
2209     /*
2210      * Make the public point out of range by adding the field (which will still
2211      * be the same point on the curve). The add is different for char2 fields.
2212      */
2213     type = EC_GROUP_get_field_type(group);
2214 #ifndef OPENSSL_NO_EC2M
2215     if (type == NID_X9_62_characteristic_two_field) {
2216         /* test for binary curves */
2217         if (!TEST_true(BN_GF2m_add(x, x, field)))
2218             goto err;
2219     } else
2220 #endif
2221     if (type == NID_X9_62_prime_field) {
2222         /* test for prime curves */
2223         if (!TEST_true(BN_add(x, x, field)))
2224             goto err;
2225     } else {
2226         /* this should never happen */
2227         TEST_error("Unsupported EC_METHOD field_type");
2228         goto err;
2229     }
2230     if (!TEST_int_le(EC_KEY_set_public_key_affine_coordinates(key, x, y), 0))
2231         goto err;
2232
2233     ret = 1;
2234 err:
2235     BN_free(x);
2236     BN_free(y);
2237     EC_KEY_free(key);
2238     return ret;
2239 }
2240
2241 /*
2242  * Helper for ec_point_hex2point_test
2243  *
2244  * Self-tests EC_POINT_point2hex() against EC_POINT_hex2point() for the given
2245  * (group,P) pair.
2246  *
2247  * If P is NULL use point at infinity.
2248  */
2249 static ossl_inline
2250 int ec_point_hex2point_test_helper(const EC_GROUP *group, const EC_POINT *P,
2251                                    point_conversion_form_t form,
2252                                    BN_CTX *bnctx)
2253 {
2254     int ret = 0;
2255     EC_POINT *Q = NULL, *Pinf = NULL;
2256     char *hex = NULL;
2257
2258     if (P == NULL) {
2259         /* If P is NULL use point at infinity. */
2260         if (!TEST_ptr(Pinf = EC_POINT_new(group))
2261                 || !TEST_true(EC_POINT_set_to_infinity(group, Pinf)))
2262             goto err;
2263         P = Pinf;
2264     }
2265
2266     if (!TEST_ptr(hex = EC_POINT_point2hex(group, P, form, bnctx))
2267             || !TEST_ptr(Q = EC_POINT_hex2point(group, hex, NULL, bnctx))
2268             || !TEST_int_eq(0, EC_POINT_cmp(group, Q, P, bnctx)))
2269         goto err;
2270
2271     /*
2272      * The next check is most likely superfluous, as EC_POINT_cmp should already
2273      * cover this.
2274      * Nonetheless it increases the test coverage for EC_POINT_is_at_infinity,
2275      * so we include it anyway!
2276      */
2277     if (Pinf != NULL
2278             && !TEST_true(EC_POINT_is_at_infinity(group, Q)))
2279         goto err;
2280
2281     ret = 1;
2282
2283  err:
2284     EC_POINT_free(Pinf);
2285     OPENSSL_free(hex);
2286     EC_POINT_free(Q);
2287
2288     return ret;
2289 }
2290
2291 /*
2292  * This test self-validates EC_POINT_hex2point() and EC_POINT_point2hex()
2293  */
2294 static int ec_point_hex2point_test(int id)
2295 {
2296     int ret = 0, nid;
2297     EC_GROUP *group = NULL;
2298     const EC_POINT *G = NULL;
2299     EC_POINT *P = NULL;
2300     BN_CTX * bnctx = NULL;
2301
2302     /* Do some setup */
2303     nid = curves[id].nid;
2304     if (!TEST_ptr(bnctx = BN_CTX_new())
2305             || !TEST_ptr(group = EC_GROUP_new_by_curve_name(nid))
2306             || !TEST_ptr(G = EC_GROUP_get0_generator(group))
2307             || !TEST_ptr(P = EC_POINT_dup(G, group)))
2308         goto err;
2309
2310     if (!TEST_true(ec_point_hex2point_test_helper(group, P,
2311                                                   POINT_CONVERSION_COMPRESSED,
2312                                                   bnctx))
2313             || !TEST_true(ec_point_hex2point_test_helper(group, NULL,
2314                                                          POINT_CONVERSION_COMPRESSED,
2315                                                          bnctx))
2316             || !TEST_true(ec_point_hex2point_test_helper(group, P,
2317                                                          POINT_CONVERSION_UNCOMPRESSED,
2318                                                          bnctx))
2319             || !TEST_true(ec_point_hex2point_test_helper(group, NULL,
2320                                                          POINT_CONVERSION_UNCOMPRESSED,
2321                                                          bnctx))
2322             || !TEST_true(ec_point_hex2point_test_helper(group, P,
2323                                                          POINT_CONVERSION_HYBRID,
2324                                                          bnctx))
2325             || !TEST_true(ec_point_hex2point_test_helper(group, NULL,
2326                                                          POINT_CONVERSION_HYBRID,
2327                                                          bnctx)))
2328         goto err;
2329
2330     ret = 1;
2331
2332  err:
2333     EC_POINT_free(P);
2334     EC_GROUP_free(group);
2335     BN_CTX_free(bnctx);
2336
2337     return ret;
2338 }
2339
2340 #endif /* OPENSSL_NO_EC */
2341
2342 int setup_tests(void)
2343 {
2344 #ifndef OPENSSL_NO_EC
2345     crv_len = EC_get_builtin_curves(NULL, 0);
2346     if (!TEST_ptr(curves = OPENSSL_malloc(sizeof(*curves) * crv_len))
2347         || !TEST_true(EC_get_builtin_curves(curves, crv_len)))
2348         return 0;
2349
2350     ADD_TEST(parameter_test);
2351     ADD_TEST(cofactor_range_test);
2352     ADD_ALL_TESTS(cardinality_test, crv_len);
2353     ADD_TEST(prime_field_tests);
2354 # ifndef OPENSSL_NO_EC2M
2355     ADD_TEST(char2_field_tests);
2356     ADD_ALL_TESTS(char2_curve_test, OSSL_NELEM(char2_curve_tests));
2357 # endif
2358     ADD_ALL_TESTS(nistp_single_test, OSSL_NELEM(nistp_tests_params));
2359     ADD_ALL_TESTS(internal_curve_test, crv_len);
2360     ADD_ALL_TESTS(internal_curve_test_method, crv_len);
2361     ADD_TEST(group_field_test);
2362     ADD_ALL_TESTS(check_named_curve_test, crv_len);
2363     ADD_ALL_TESTS(check_named_curve_lookup_test, crv_len);
2364     ADD_ALL_TESTS(check_ec_key_field_public_range_test, crv_len);
2365     ADD_ALL_TESTS(check_named_curve_from_ecparameters, crv_len);
2366     ADD_ALL_TESTS(ec_point_hex2point_test, crv_len);
2367 #endif /* OPENSSL_NO_EC */
2368     return 1;
2369 }
2370
2371 void cleanup_tests(void)
2372 {
2373 #ifndef OPENSSL_NO_EC
2374     OPENSSL_free(curves);
2375 #endif
2376 }