BN_mod_exp_mont_consttime: check for zero modulus.
[oweals/openssl.git] / crypto / bn / bntest.c
1 /* crypto/bn/bntest.c */
2 /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
3  * All rights reserved.
4  *
5  * This package is an SSL implementation written
6  * by Eric Young (eay@cryptsoft.com).
7  * The implementation was written so as to conform with Netscapes SSL.
8  *
9  * This library is free for commercial and non-commercial use as long as
10  * the following conditions are aheared to.  The following conditions
11  * apply to all code found in this distribution, be it the RC4, RSA,
12  * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
13  * included with this distribution is covered by the same copyright terms
14  * except that the holder is Tim Hudson (tjh@cryptsoft.com).
15  *
16  * Copyright remains Eric Young's, and as such any Copyright notices in
17  * the code are not to be removed.
18  * If this package is used in a product, Eric Young should be given attribution
19  * as the author of the parts of the library used.
20  * This can be in the form of a textual message at program startup or
21  * in documentation (online or textual) provided with the package.
22  *
23  * Redistribution and use in source and binary forms, with or without
24  * modification, are permitted provided that the following conditions
25  * are met:
26  * 1. Redistributions of source code must retain the copyright
27  *    notice, this list of conditions and the following disclaimer.
28  * 2. Redistributions in binary form must reproduce the above copyright
29  *    notice, this list of conditions and the following disclaimer in the
30  *    documentation and/or other materials provided with the distribution.
31  * 3. All advertising materials mentioning features or use of this software
32  *    must display the following acknowledgement:
33  *    "This product includes cryptographic software written by
34  *     Eric Young (eay@cryptsoft.com)"
35  *    The word 'cryptographic' can be left out if the rouines from the library
36  *    being used are not cryptographic related :-).
37  * 4. If you include any Windows specific code (or a derivative thereof) from
38  *    the apps directory (application code) you must include an acknowledgement:
39  *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
40  *
41  * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
42  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
43  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
44  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
45  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
46  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
47  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
48  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
49  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
50  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
51  * SUCH DAMAGE.
52  *
53  * The licence and distribution terms for any publically available version or
54  * derivative of this code cannot be changed.  i.e. this code cannot simply be
55  * copied and put under another distribution licence
56  * [including the GNU Public Licence.]
57  */
58 /* ====================================================================
59  * Copyright 2002 Sun Microsystems, Inc. ALL RIGHTS RESERVED.
60  *
61  * Portions of the attached software ("Contribution") are developed by
62  * SUN MICROSYSTEMS, INC., and are contributed to the OpenSSL project.
63  *
64  * The Contribution is licensed pursuant to the Eric Young open source
65  * license provided above.
66  *
67  * The binary polynomial arithmetic software is originally written by
68  * Sheueling Chang Shantz and Douglas Stebila of Sun Microsystems Laboratories.
69  *
70  */
71
72 /*
73  * Until the key-gen callbacks are modified to use newer prototypes, we allow
74  * deprecated functions for openssl-internal code
75  */
76 #ifdef OPENSSL_NO_DEPRECATED
77 # undef OPENSSL_NO_DEPRECATED
78 #endif
79
80 #include <stdio.h>
81 #include <stdlib.h>
82 #include <string.h>
83
84 #include "e_os.h"
85
86 #include <openssl/bio.h>
87 #include <openssl/bn.h>
88 #include <openssl/rand.h>
89 #include <openssl/x509.h>
90 #include <openssl/err.h>
91
92 const int num0 = 100;           /* number of tests */
93 const int num1 = 50;            /* additional tests for some functions */
94 const int num2 = 5;             /* number of tests for slow functions */
95
96 int test_add(BIO *bp);
97 int test_sub(BIO *bp);
98 int test_lshift1(BIO *bp);
99 int test_lshift(BIO *bp, BN_CTX *ctx, BIGNUM *a_);
100 int test_rshift1(BIO *bp);
101 int test_rshift(BIO *bp, BN_CTX *ctx);
102 int test_div(BIO *bp, BN_CTX *ctx);
103 int test_div_word(BIO *bp);
104 int test_div_recp(BIO *bp, BN_CTX *ctx);
105 int test_mul(BIO *bp);
106 int test_sqr(BIO *bp, BN_CTX *ctx);
107 int test_mont(BIO *bp, BN_CTX *ctx);
108 int test_mod(BIO *bp, BN_CTX *ctx);
109 int test_mod_mul(BIO *bp, BN_CTX *ctx);
110 int test_mod_exp(BIO *bp, BN_CTX *ctx);
111 int test_mod_exp_mont_consttime(BIO *bp, BN_CTX *ctx);
112 int test_mod_exp_mont5(BIO *bp, BN_CTX *ctx);
113 int test_exp(BIO *bp, BN_CTX *ctx);
114 int test_gf2m_add(BIO *bp);
115 int test_gf2m_mod(BIO *bp);
116 int test_gf2m_mod_mul(BIO *bp, BN_CTX *ctx);
117 int test_gf2m_mod_sqr(BIO *bp, BN_CTX *ctx);
118 int test_gf2m_mod_inv(BIO *bp, BN_CTX *ctx);
119 int test_gf2m_mod_div(BIO *bp, BN_CTX *ctx);
120 int test_gf2m_mod_exp(BIO *bp, BN_CTX *ctx);
121 int test_gf2m_mod_sqrt(BIO *bp, BN_CTX *ctx);
122 int test_gf2m_mod_solve_quad(BIO *bp, BN_CTX *ctx);
123 int test_kron(BIO *bp, BN_CTX *ctx);
124 int test_sqrt(BIO *bp, BN_CTX *ctx);
125 int rand_neg(void);
126 static int results = 0;
127
128 static unsigned char lst[] =
129     "\xC6\x4F\x43\x04\x2A\xEA\xCA\x6E\x58\x36\x80\x5B\xE8\xC9"
130     "\x9B\x04\x5D\x48\x36\xC2\xFD\x16\xC9\x64\xF0";
131
132 static const char rnd_seed[] =
133     "string to make the random number generator think it has entropy";
134
135 static void message(BIO *out, char *m)
136 {
137     fprintf(stderr, "test %s\n", m);
138     BIO_puts(out, "print \"test ");
139     BIO_puts(out, m);
140     BIO_puts(out, "\\n\"\n");
141 }
142
143 int main(int argc, char *argv[])
144 {
145     BN_CTX *ctx;
146     BIO *out;
147     char *outfile = NULL;
148
149     results = 0;
150
151     RAND_seed(rnd_seed, sizeof rnd_seed); /* or BN_generate_prime may fail */
152
153     argc--;
154     argv++;
155     while (argc >= 1) {
156         if (strcmp(*argv, "-results") == 0)
157             results = 1;
158         else if (strcmp(*argv, "-out") == 0) {
159             if (--argc < 1)
160                 break;
161             outfile = *(++argv);
162         }
163         argc--;
164         argv++;
165     }
166
167     ctx = BN_CTX_new();
168     if (ctx == NULL)
169         EXIT(1);
170
171     out = BIO_new(BIO_s_file());
172     if (out == NULL)
173         EXIT(1);
174     if (outfile == NULL) {
175         BIO_set_fp(out, stdout, BIO_NOCLOSE);
176     } else {
177         if (!BIO_write_filename(out, outfile)) {
178             perror(outfile);
179             EXIT(1);
180         }
181     }
182
183     if (!results)
184         BIO_puts(out, "obase=16\nibase=16\n");
185
186     message(out, "BN_add");
187     if (!test_add(out))
188         goto err;
189     (void)BIO_flush(out);
190
191     message(out, "BN_sub");
192     if (!test_sub(out))
193         goto err;
194     (void)BIO_flush(out);
195
196     message(out, "BN_lshift1");
197     if (!test_lshift1(out))
198         goto err;
199     (void)BIO_flush(out);
200
201     message(out, "BN_lshift (fixed)");
202     if (!test_lshift(out, ctx, BN_bin2bn(lst, sizeof(lst) - 1, NULL)))
203         goto err;
204     (void)BIO_flush(out);
205
206     message(out, "BN_lshift");
207     if (!test_lshift(out, ctx, NULL))
208         goto err;
209     (void)BIO_flush(out);
210
211     message(out, "BN_rshift1");
212     if (!test_rshift1(out))
213         goto err;
214     (void)BIO_flush(out);
215
216     message(out, "BN_rshift");
217     if (!test_rshift(out, ctx))
218         goto err;
219     (void)BIO_flush(out);
220
221     message(out, "BN_sqr");
222     if (!test_sqr(out, ctx))
223         goto err;
224     (void)BIO_flush(out);
225
226     message(out, "BN_mul");
227     if (!test_mul(out))
228         goto err;
229     (void)BIO_flush(out);
230
231     message(out, "BN_div");
232     if (!test_div(out, ctx))
233         goto err;
234     (void)BIO_flush(out);
235
236     message(out, "BN_div_word");
237     if (!test_div_word(out))
238         goto err;
239     (void)BIO_flush(out);
240
241     message(out, "BN_div_recp");
242     if (!test_div_recp(out, ctx))
243         goto err;
244     (void)BIO_flush(out);
245
246     message(out, "BN_mod");
247     if (!test_mod(out, ctx))
248         goto err;
249     (void)BIO_flush(out);
250
251     message(out, "BN_mod_mul");
252     if (!test_mod_mul(out, ctx))
253         goto err;
254     (void)BIO_flush(out);
255
256     message(out, "BN_mont");
257     if (!test_mont(out, ctx))
258         goto err;
259     (void)BIO_flush(out);
260
261     message(out, "BN_mod_exp");
262     if (!test_mod_exp(out, ctx))
263         goto err;
264     (void)BIO_flush(out);
265
266     message(out, "BN_mod_exp_mont_consttime");
267     if (!test_mod_exp_mont_consttime(out, ctx))
268         goto err;
269     if (!test_mod_exp_mont5(out, ctx))
270         goto err;
271     (void)BIO_flush(out);
272
273     message(out, "BN_exp");
274     if (!test_exp(out, ctx))
275         goto err;
276     (void)BIO_flush(out);
277
278     message(out, "BN_kronecker");
279     if (!test_kron(out, ctx))
280         goto err;
281     (void)BIO_flush(out);
282
283     message(out, "BN_mod_sqrt");
284     if (!test_sqrt(out, ctx))
285         goto err;
286     (void)BIO_flush(out);
287 #ifndef OPENSSL_NO_EC2M
288     message(out, "BN_GF2m_add");
289     if (!test_gf2m_add(out))
290         goto err;
291     (void)BIO_flush(out);
292
293     message(out, "BN_GF2m_mod");
294     if (!test_gf2m_mod(out))
295         goto err;
296     (void)BIO_flush(out);
297
298     message(out, "BN_GF2m_mod_mul");
299     if (!test_gf2m_mod_mul(out, ctx))
300         goto err;
301     (void)BIO_flush(out);
302
303     message(out, "BN_GF2m_mod_sqr");
304     if (!test_gf2m_mod_sqr(out, ctx))
305         goto err;
306     (void)BIO_flush(out);
307
308     message(out, "BN_GF2m_mod_inv");
309     if (!test_gf2m_mod_inv(out, ctx))
310         goto err;
311     (void)BIO_flush(out);
312
313     message(out, "BN_GF2m_mod_div");
314     if (!test_gf2m_mod_div(out, ctx))
315         goto err;
316     (void)BIO_flush(out);
317
318     message(out, "BN_GF2m_mod_exp");
319     if (!test_gf2m_mod_exp(out, ctx))
320         goto err;
321     (void)BIO_flush(out);
322
323     message(out, "BN_GF2m_mod_sqrt");
324     if (!test_gf2m_mod_sqrt(out, ctx))
325         goto err;
326     (void)BIO_flush(out);
327
328     message(out, "BN_GF2m_mod_solve_quad");
329     if (!test_gf2m_mod_solve_quad(out, ctx))
330         goto err;
331     (void)BIO_flush(out);
332 #endif
333     BN_CTX_free(ctx);
334     BIO_free(out);
335
336     EXIT(0);
337  err:
338     BIO_puts(out, "1\n");       /* make sure the Perl script fed by bc
339                                  * notices the failure, see test_bn in
340                                  * test/Makefile.ssl */
341     (void)BIO_flush(out);
342     ERR_load_crypto_strings();
343     ERR_print_errors_fp(stderr);
344     EXIT(1);
345     return (1);
346 }
347
348 int test_add(BIO *bp)
349 {
350     BIGNUM a, b, c;
351     int i;
352
353     BN_init(&a);
354     BN_init(&b);
355     BN_init(&c);
356
357     BN_bntest_rand(&a, 512, 0, 0);
358     for (i = 0; i < num0; i++) {
359         BN_bntest_rand(&b, 450 + i, 0, 0);
360         a.neg = rand_neg();
361         b.neg = rand_neg();
362         BN_add(&c, &a, &b);
363         if (bp != NULL) {
364             if (!results) {
365                 BN_print(bp, &a);
366                 BIO_puts(bp, " + ");
367                 BN_print(bp, &b);
368                 BIO_puts(bp, " - ");
369             }
370             BN_print(bp, &c);
371             BIO_puts(bp, "\n");
372         }
373         a.neg = !a.neg;
374         b.neg = !b.neg;
375         BN_add(&c, &c, &b);
376         BN_add(&c, &c, &a);
377         if (!BN_is_zero(&c)) {
378             fprintf(stderr, "Add test failed!\n");
379             return 0;
380         }
381     }
382     BN_free(&a);
383     BN_free(&b);
384     BN_free(&c);
385     return (1);
386 }
387
388 int test_sub(BIO *bp)
389 {
390     BIGNUM a, b, c;
391     int i;
392
393     BN_init(&a);
394     BN_init(&b);
395     BN_init(&c);
396
397     for (i = 0; i < num0 + num1; i++) {
398         if (i < num1) {
399             BN_bntest_rand(&a, 512, 0, 0);
400             BN_copy(&b, &a);
401             if (BN_set_bit(&a, i) == 0)
402                 return (0);
403             BN_add_word(&b, i);
404         } else {
405             BN_bntest_rand(&b, 400 + i - num1, 0, 0);
406             a.neg = rand_neg();
407             b.neg = rand_neg();
408         }
409         BN_sub(&c, &a, &b);
410         if (bp != NULL) {
411             if (!results) {
412                 BN_print(bp, &a);
413                 BIO_puts(bp, " - ");
414                 BN_print(bp, &b);
415                 BIO_puts(bp, " - ");
416             }
417             BN_print(bp, &c);
418             BIO_puts(bp, "\n");
419         }
420         BN_add(&c, &c, &b);
421         BN_sub(&c, &c, &a);
422         if (!BN_is_zero(&c)) {
423             fprintf(stderr, "Subtract test failed!\n");
424             return 0;
425         }
426     }
427     BN_free(&a);
428     BN_free(&b);
429     BN_free(&c);
430     return (1);
431 }
432
433 int test_div(BIO *bp, BN_CTX *ctx)
434 {
435     BIGNUM a, b, c, d, e;
436     int i;
437
438     BN_init(&a);
439     BN_init(&b);
440     BN_init(&c);
441     BN_init(&d);
442     BN_init(&e);
443
444     BN_one(&a);
445     BN_zero(&b);
446
447     if (BN_div(&d, &c, &a, &b, ctx)) {
448         fprintf(stderr, "Division by zero succeeded!\n");
449         return 0;
450     }
451
452     for (i = 0; i < num0 + num1; i++) {
453         if (i < num1) {
454             BN_bntest_rand(&a, 400, 0, 0);
455             BN_copy(&b, &a);
456             BN_lshift(&a, &a, i);
457             BN_add_word(&a, i);
458         } else
459             BN_bntest_rand(&b, 50 + 3 * (i - num1), 0, 0);
460         a.neg = rand_neg();
461         b.neg = rand_neg();
462         BN_div(&d, &c, &a, &b, ctx);
463         if (bp != NULL) {
464             if (!results) {
465                 BN_print(bp, &a);
466                 BIO_puts(bp, " / ");
467                 BN_print(bp, &b);
468                 BIO_puts(bp, " - ");
469             }
470             BN_print(bp, &d);
471             BIO_puts(bp, "\n");
472
473             if (!results) {
474                 BN_print(bp, &a);
475                 BIO_puts(bp, " % ");
476                 BN_print(bp, &b);
477                 BIO_puts(bp, " - ");
478             }
479             BN_print(bp, &c);
480             BIO_puts(bp, "\n");
481         }
482         BN_mul(&e, &d, &b, ctx);
483         BN_add(&d, &e, &c);
484         BN_sub(&d, &d, &a);
485         if (!BN_is_zero(&d)) {
486             fprintf(stderr, "Division test failed!\n");
487             return 0;
488         }
489     }
490     BN_free(&a);
491     BN_free(&b);
492     BN_free(&c);
493     BN_free(&d);
494     BN_free(&e);
495     return (1);
496 }
497
498 static void print_word(BIO *bp, BN_ULONG w)
499 {
500 #ifdef SIXTY_FOUR_BIT
501     if (sizeof(w) > sizeof(unsigned long)) {
502         unsigned long h = (unsigned long)(w >> 32), l = (unsigned long)(w);
503
504         if (h)
505             BIO_printf(bp, "%lX%08lX", h, l);
506         else
507             BIO_printf(bp, "%lX", l);
508         return;
509     }
510 #endif
511     BIO_printf(bp, BN_HEX_FMT1, w);
512 }
513
514 int test_div_word(BIO *bp)
515 {
516     BIGNUM a, b;
517     BN_ULONG r, s;
518     int i;
519
520     BN_init(&a);
521     BN_init(&b);
522
523     for (i = 0; i < num0; i++) {
524         do {
525             BN_bntest_rand(&a, 512, -1, 0);
526             BN_bntest_rand(&b, BN_BITS2, -1, 0);
527         } while (BN_is_zero(&b));
528
529         s = b.d[0];
530         BN_copy(&b, &a);
531         r = BN_div_word(&b, s);
532
533         if (bp != NULL) {
534             if (!results) {
535                 BN_print(bp, &a);
536                 BIO_puts(bp, " / ");
537                 print_word(bp, s);
538                 BIO_puts(bp, " - ");
539             }
540             BN_print(bp, &b);
541             BIO_puts(bp, "\n");
542
543             if (!results) {
544                 BN_print(bp, &a);
545                 BIO_puts(bp, " % ");
546                 print_word(bp, s);
547                 BIO_puts(bp, " - ");
548             }
549             print_word(bp, r);
550             BIO_puts(bp, "\n");
551         }
552         BN_mul_word(&b, s);
553         BN_add_word(&b, r);
554         BN_sub(&b, &a, &b);
555         if (!BN_is_zero(&b)) {
556             fprintf(stderr, "Division (word) test failed!\n");
557             return 0;
558         }
559     }
560     BN_free(&a);
561     BN_free(&b);
562     return (1);
563 }
564
565 int test_div_recp(BIO *bp, BN_CTX *ctx)
566 {
567     BIGNUM a, b, c, d, e;
568     BN_RECP_CTX recp;
569     int i;
570
571     BN_RECP_CTX_init(&recp);
572     BN_init(&a);
573     BN_init(&b);
574     BN_init(&c);
575     BN_init(&d);
576     BN_init(&e);
577
578     for (i = 0; i < num0 + num1; i++) {
579         if (i < num1) {
580             BN_bntest_rand(&a, 400, 0, 0);
581             BN_copy(&b, &a);
582             BN_lshift(&a, &a, i);
583             BN_add_word(&a, i);
584         } else
585             BN_bntest_rand(&b, 50 + 3 * (i - num1), 0, 0);
586         a.neg = rand_neg();
587         b.neg = rand_neg();
588         BN_RECP_CTX_set(&recp, &b, ctx);
589         BN_div_recp(&d, &c, &a, &recp, ctx);
590         if (bp != NULL) {
591             if (!results) {
592                 BN_print(bp, &a);
593                 BIO_puts(bp, " / ");
594                 BN_print(bp, &b);
595                 BIO_puts(bp, " - ");
596             }
597             BN_print(bp, &d);
598             BIO_puts(bp, "\n");
599
600             if (!results) {
601                 BN_print(bp, &a);
602                 BIO_puts(bp, " % ");
603                 BN_print(bp, &b);
604                 BIO_puts(bp, " - ");
605             }
606             BN_print(bp, &c);
607             BIO_puts(bp, "\n");
608         }
609         BN_mul(&e, &d, &b, ctx);
610         BN_add(&d, &e, &c);
611         BN_sub(&d, &d, &a);
612         if (!BN_is_zero(&d)) {
613             fprintf(stderr, "Reciprocal division test failed!\n");
614             fprintf(stderr, "a=");
615             BN_print_fp(stderr, &a);
616             fprintf(stderr, "\nb=");
617             BN_print_fp(stderr, &b);
618             fprintf(stderr, "\n");
619             return 0;
620         }
621     }
622     BN_free(&a);
623     BN_free(&b);
624     BN_free(&c);
625     BN_free(&d);
626     BN_free(&e);
627     BN_RECP_CTX_free(&recp);
628     return (1);
629 }
630
631 int test_mul(BIO *bp)
632 {
633     BIGNUM a, b, c, d, e;
634     int i;
635     BN_CTX *ctx;
636
637     ctx = BN_CTX_new();
638     if (ctx == NULL)
639         EXIT(1);
640
641     BN_init(&a);
642     BN_init(&b);
643     BN_init(&c);
644     BN_init(&d);
645     BN_init(&e);
646
647     for (i = 0; i < num0 + num1; i++) {
648         if (i <= num1) {
649             BN_bntest_rand(&a, 100, 0, 0);
650             BN_bntest_rand(&b, 100, 0, 0);
651         } else
652             BN_bntest_rand(&b, i - num1, 0, 0);
653         a.neg = rand_neg();
654         b.neg = rand_neg();
655         BN_mul(&c, &a, &b, ctx);
656         if (bp != NULL) {
657             if (!results) {
658                 BN_print(bp, &a);
659                 BIO_puts(bp, " * ");
660                 BN_print(bp, &b);
661                 BIO_puts(bp, " - ");
662             }
663             BN_print(bp, &c);
664             BIO_puts(bp, "\n");
665         }
666         BN_div(&d, &e, &c, &a, ctx);
667         BN_sub(&d, &d, &b);
668         if (!BN_is_zero(&d) || !BN_is_zero(&e)) {
669             fprintf(stderr, "Multiplication test failed!\n");
670             return 0;
671         }
672     }
673     BN_free(&a);
674     BN_free(&b);
675     BN_free(&c);
676     BN_free(&d);
677     BN_free(&e);
678     BN_CTX_free(ctx);
679     return (1);
680 }
681
682 int test_sqr(BIO *bp, BN_CTX *ctx)
683 {
684     BIGNUM *a, *c, *d, *e;
685     int i, ret = 0;
686
687     a = BN_new();
688     c = BN_new();
689     d = BN_new();
690     e = BN_new();
691     if (a == NULL || c == NULL || d == NULL || e == NULL) {
692         goto err;
693     }
694
695     for (i = 0; i < num0; i++) {
696         BN_bntest_rand(a, 40 + i * 10, 0, 0);
697         a->neg = rand_neg();
698         BN_sqr(c, a, ctx);
699         if (bp != NULL) {
700             if (!results) {
701                 BN_print(bp, a);
702                 BIO_puts(bp, " * ");
703                 BN_print(bp, a);
704                 BIO_puts(bp, " - ");
705             }
706             BN_print(bp, c);
707             BIO_puts(bp, "\n");
708         }
709         BN_div(d, e, c, a, ctx);
710         BN_sub(d, d, a);
711         if (!BN_is_zero(d) || !BN_is_zero(e)) {
712             fprintf(stderr, "Square test failed!\n");
713             goto err;
714         }
715     }
716
717     /* Regression test for a BN_sqr overflow bug. */
718     BN_hex2bn(&a,
719               "80000000000000008000000000000001"
720               "FFFFFFFFFFFFFFFE0000000000000000");
721     BN_sqr(c, a, ctx);
722     if (bp != NULL) {
723         if (!results) {
724             BN_print(bp, a);
725             BIO_puts(bp, " * ");
726             BN_print(bp, a);
727             BIO_puts(bp, " - ");
728         }
729         BN_print(bp, c);
730         BIO_puts(bp, "\n");
731     }
732     BN_mul(d, a, a, ctx);
733     if (BN_cmp(c, d)) {
734         fprintf(stderr, "Square test failed: BN_sqr and BN_mul produce "
735                 "different results!\n");
736         goto err;
737     }
738
739     /* Regression test for a BN_sqr overflow bug. */
740     BN_hex2bn(&a,
741               "80000000000000000000000080000001"
742               "FFFFFFFE000000000000000000000000");
743     BN_sqr(c, a, ctx);
744     if (bp != NULL) {
745         if (!results) {
746             BN_print(bp, a);
747             BIO_puts(bp, " * ");
748             BN_print(bp, a);
749             BIO_puts(bp, " - ");
750         }
751         BN_print(bp, c);
752         BIO_puts(bp, "\n");
753     }
754     BN_mul(d, a, a, ctx);
755     if (BN_cmp(c, d)) {
756         fprintf(stderr, "Square test failed: BN_sqr and BN_mul produce "
757                 "different results!\n");
758         goto err;
759     }
760     ret = 1;
761  err:
762     if (a != NULL)
763         BN_free(a);
764     if (c != NULL)
765         BN_free(c);
766     if (d != NULL)
767         BN_free(d);
768     if (e != NULL)
769         BN_free(e);
770     return ret;
771 }
772
773 int test_mont(BIO *bp, BN_CTX *ctx)
774 {
775     BIGNUM a, b, c, d, A, B;
776     BIGNUM n;
777     int i;
778     BN_MONT_CTX *mont;
779
780     BN_init(&a);
781     BN_init(&b);
782     BN_init(&c);
783     BN_init(&d);
784     BN_init(&A);
785     BN_init(&B);
786     BN_init(&n);
787
788     mont = BN_MONT_CTX_new();
789     if (mont == NULL)
790         return 0;
791
792     BN_zero(&n);
793     if (BN_MONT_CTX_set(mont, &n, ctx)) {
794         fprintf(stderr, "BN_MONT_CTX_set succeeded for zero modulus!\n");
795         return 0;
796     }
797
798     BN_set_word(&n, 16);
799     if (BN_MONT_CTX_set(mont, &n, ctx)) {
800         fprintf(stderr, "BN_MONT_CTX_set succeeded for even modulus!\n");
801         return 0;
802     }
803
804     BN_bntest_rand(&a, 100, 0, 0);
805     BN_bntest_rand(&b, 100, 0, 0);
806     for (i = 0; i < num2; i++) {
807         int bits = (200 * (i + 1)) / num2;
808
809         if (bits == 0)
810             continue;
811         BN_bntest_rand(&n, bits, 0, 1);
812         BN_MONT_CTX_set(mont, &n, ctx);
813
814         BN_nnmod(&a, &a, &n, ctx);
815         BN_nnmod(&b, &b, &n, ctx);
816
817         BN_to_montgomery(&A, &a, mont, ctx);
818         BN_to_montgomery(&B, &b, mont, ctx);
819
820         BN_mod_mul_montgomery(&c, &A, &B, mont, ctx);
821         BN_from_montgomery(&A, &c, mont, ctx);
822         if (bp != NULL) {
823             if (!results) {
824 #ifdef undef
825                 fprintf(stderr, "%d * %d %% %d\n",
826                         BN_num_bits(&a),
827                         BN_num_bits(&b), BN_num_bits(mont->N));
828 #endif
829                 BN_print(bp, &a);
830                 BIO_puts(bp, " * ");
831                 BN_print(bp, &b);
832                 BIO_puts(bp, " % ");
833                 BN_print(bp, &(mont->N));
834                 BIO_puts(bp, " - ");
835             }
836             BN_print(bp, &A);
837             BIO_puts(bp, "\n");
838         }
839         BN_mod_mul(&d, &a, &b, &n, ctx);
840         BN_sub(&d, &d, &A);
841         if (!BN_is_zero(&d)) {
842             fprintf(stderr, "Montgomery multiplication test failed!\n");
843             return 0;
844         }
845     }
846     BN_MONT_CTX_free(mont);
847     BN_free(&a);
848     BN_free(&b);
849     BN_free(&c);
850     BN_free(&d);
851     BN_free(&A);
852     BN_free(&B);
853     BN_free(&n);
854     return (1);
855 }
856
857 int test_mod(BIO *bp, BN_CTX *ctx)
858 {
859     BIGNUM *a, *b, *c, *d, *e;
860     int i;
861
862     a = BN_new();
863     b = BN_new();
864     c = BN_new();
865     d = BN_new();
866     e = BN_new();
867
868     BN_bntest_rand(a, 1024, 0, 0);
869     for (i = 0; i < num0; i++) {
870         BN_bntest_rand(b, 450 + i * 10, 0, 0);
871         a->neg = rand_neg();
872         b->neg = rand_neg();
873         BN_mod(c, a, b, ctx);
874         if (bp != NULL) {
875             if (!results) {
876                 BN_print(bp, a);
877                 BIO_puts(bp, " % ");
878                 BN_print(bp, b);
879                 BIO_puts(bp, " - ");
880             }
881             BN_print(bp, c);
882             BIO_puts(bp, "\n");
883         }
884         BN_div(d, e, a, b, ctx);
885         BN_sub(e, e, c);
886         if (!BN_is_zero(e)) {
887             fprintf(stderr, "Modulo test failed!\n");
888             return 0;
889         }
890     }
891     BN_free(a);
892     BN_free(b);
893     BN_free(c);
894     BN_free(d);
895     BN_free(e);
896     return (1);
897 }
898
899 int test_mod_mul(BIO *bp, BN_CTX *ctx)
900 {
901     BIGNUM *a, *b, *c, *d, *e;
902     int i, j;
903
904     a = BN_new();
905     b = BN_new();
906     c = BN_new();
907     d = BN_new();
908     e = BN_new();
909
910     BN_one(a);
911     BN_one(b);
912     BN_zero(c);
913     if (BN_mod_mul(e, a, b, c, ctx)) {
914         fprintf(stderr, "BN_mod_mul with zero modulus succeeded!\n");
915         return 0;
916     }
917
918     for (j = 0; j < 3; j++) {
919         BN_bntest_rand(c, 1024, 0, 0);
920         for (i = 0; i < num0; i++) {
921             BN_bntest_rand(a, 475 + i * 10, 0, 0);
922             BN_bntest_rand(b, 425 + i * 11, 0, 0);
923             a->neg = rand_neg();
924             b->neg = rand_neg();
925             if (!BN_mod_mul(e, a, b, c, ctx)) {
926                 unsigned long l;
927
928                 while ((l = ERR_get_error()))
929                     fprintf(stderr, "ERROR:%s\n", ERR_error_string(l, NULL));
930                 EXIT(1);
931             }
932             if (bp != NULL) {
933                 if (!results) {
934                     BN_print(bp, a);
935                     BIO_puts(bp, " * ");
936                     BN_print(bp, b);
937                     BIO_puts(bp, " % ");
938                     BN_print(bp, c);
939                     if ((a->neg ^ b->neg) && !BN_is_zero(e)) {
940                         /*
941                          * If (a*b) % c is negative, c must be added in order
942                          * to obtain the normalized remainder (new with
943                          * OpenSSL 0.9.7, previous versions of BN_mod_mul
944                          * could generate negative results)
945                          */
946                         BIO_puts(bp, " + ");
947                         BN_print(bp, c);
948                     }
949                     BIO_puts(bp, " - ");
950                 }
951                 BN_print(bp, e);
952                 BIO_puts(bp, "\n");
953             }
954             BN_mul(d, a, b, ctx);
955             BN_sub(d, d, e);
956             BN_div(a, b, d, c, ctx);
957             if (!BN_is_zero(b)) {
958                 fprintf(stderr, "Modulo multiply test failed!\n");
959                 ERR_print_errors_fp(stderr);
960                 return 0;
961             }
962         }
963     }
964     BN_free(a);
965     BN_free(b);
966     BN_free(c);
967     BN_free(d);
968     BN_free(e);
969     return (1);
970 }
971
972 int test_mod_exp(BIO *bp, BN_CTX *ctx)
973 {
974     BIGNUM *a, *b, *c, *d, *e;
975     int i;
976
977     a = BN_new();
978     b = BN_new();
979     c = BN_new();
980     d = BN_new();
981     e = BN_new();
982
983     BN_one(a);
984     BN_one(b);
985     BN_zero(c);
986     if (BN_mod_exp(d, a, b, c, ctx)) {
987         fprintf(stderr, "BN_mod_exp with zero modulus succeeded!\n");
988         return 0;
989     }
990
991     BN_bntest_rand(c, 30, 0, 1); /* must be odd for montgomery */
992     for (i = 0; i < num2; i++) {
993         BN_bntest_rand(a, 20 + i * 5, 0, 0);
994         BN_bntest_rand(b, 2 + i, 0, 0);
995
996         if (!BN_mod_exp(d, a, b, c, ctx))
997             return (0);
998
999         if (bp != NULL) {
1000             if (!results) {
1001                 BN_print(bp, a);
1002                 BIO_puts(bp, " ^ ");
1003                 BN_print(bp, b);
1004                 BIO_puts(bp, " % ");
1005                 BN_print(bp, c);
1006                 BIO_puts(bp, " - ");
1007             }
1008             BN_print(bp, d);
1009             BIO_puts(bp, "\n");
1010         }
1011         BN_exp(e, a, b, ctx);
1012         BN_sub(e, e, d);
1013         BN_div(a, b, e, c, ctx);
1014         if (!BN_is_zero(b)) {
1015             fprintf(stderr, "Modulo exponentiation test failed!\n");
1016             return 0;
1017         }
1018     }
1019     BN_free(a);
1020     BN_free(b);
1021     BN_free(c);
1022     BN_free(d);
1023     BN_free(e);
1024     return (1);
1025 }
1026
1027 int test_mod_exp_mont_consttime(BIO *bp, BN_CTX *ctx)
1028 {
1029     BIGNUM *a, *b, *c, *d, *e;
1030     int i;
1031
1032     a = BN_new();
1033     b = BN_new();
1034     c = BN_new();
1035     d = BN_new();
1036     e = BN_new();
1037
1038     BN_one(a);
1039     BN_one(b);
1040     BN_zero(c);
1041     if (BN_mod_exp_mont_consttime(d, a, b, c, ctx, NULL)) {
1042         fprintf(stderr, "BN_mod_exp_mont_consttime with zero modulus "
1043                 "succeeded\n");
1044         return 0;
1045     }
1046
1047     BN_set_word(c, 16);
1048     if (BN_mod_exp_mont_consttime(d, a, b, c, ctx, NULL)) {
1049         fprintf(stderr, "BN_mod_exp_mont_consttime with even modulus "
1050                 "succeeded\n");
1051         return 0;
1052     }
1053
1054     BN_bntest_rand(c, 30, 0, 1); /* must be odd for montgomery */
1055     for (i = 0; i < num2; i++) {
1056         BN_bntest_rand(a, 20 + i * 5, 0, 0);
1057         BN_bntest_rand(b, 2 + i, 0, 0);
1058
1059         if (!BN_mod_exp_mont_consttime(d, a, b, c, ctx, NULL))
1060             return (00);
1061
1062         if (bp != NULL) {
1063             if (!results) {
1064                 BN_print(bp, a);
1065                 BIO_puts(bp, " ^ ");
1066                 BN_print(bp, b);
1067                 BIO_puts(bp, " % ");
1068                 BN_print(bp, c);
1069                 BIO_puts(bp, " - ");
1070             }
1071             BN_print(bp, d);
1072             BIO_puts(bp, "\n");
1073         }
1074         BN_exp(e, a, b, ctx);
1075         BN_sub(e, e, d);
1076         BN_div(a, b, e, c, ctx);
1077         if (!BN_is_zero(b)) {
1078             fprintf(stderr, "Modulo exponentiation test failed!\n");
1079             return 0;
1080         }
1081     }
1082     BN_free(a);
1083     BN_free(b);
1084     BN_free(c);
1085     BN_free(d);
1086     BN_free(e);
1087     return (1);
1088 }
1089
1090 /*
1091  * Test constant-time modular exponentiation with 1024-bit inputs, which on
1092  * x86_64 cause a different code branch to be taken.
1093  */
1094 int test_mod_exp_mont5(BIO *bp, BN_CTX *ctx)
1095 {
1096     BIGNUM *a, *p, *m, *d, *e;
1097     BN_MONT_CTX *mont;
1098
1099     a = BN_new();
1100     p = BN_new();
1101     m = BN_new();
1102     d = BN_new();
1103     e = BN_new();
1104     mont = BN_MONT_CTX_new();
1105
1106     BN_bntest_rand(m, 1024, 0, 1); /* must be odd for montgomery */
1107     /* Zero exponent */
1108     BN_bntest_rand(a, 1024, 0, 0);
1109     BN_zero(p);
1110     if (!BN_mod_exp_mont_consttime(d, a, p, m, ctx, NULL))
1111         return 0;
1112     if (!BN_is_one(d)) {
1113         fprintf(stderr, "Modular exponentiation test failed!\n");
1114         return 0;
1115     }
1116     /* Zero input */
1117     BN_bntest_rand(p, 1024, 0, 0);
1118     BN_zero(a);
1119     if (!BN_mod_exp_mont_consttime(d, a, p, m, ctx, NULL))
1120         return 0;
1121     if (!BN_is_zero(d)) {
1122         fprintf(stderr, "Modular exponentiation test failed!\n");
1123         return 0;
1124     }
1125     /*
1126      * Craft an input whose Montgomery representation is 1, i.e., shorter
1127      * than the modulus m, in order to test the const time precomputation
1128      * scattering/gathering.
1129      */
1130     BN_one(a);
1131     BN_MONT_CTX_set(mont, m, ctx);
1132     if (!BN_from_montgomery(e, a, mont, ctx))
1133         return 0;
1134     if (!BN_mod_exp_mont_consttime(d, e, p, m, ctx, NULL))
1135         return 0;
1136     if (!BN_mod_exp_simple(a, e, p, m, ctx))
1137         return 0;
1138     if (BN_cmp(a, d) != 0) {
1139         fprintf(stderr, "Modular exponentiation test failed!\n");
1140         return 0;
1141     }
1142     /* Finally, some regular test vectors. */
1143     BN_bntest_rand(e, 1024, 0, 0);
1144     if (!BN_mod_exp_mont_consttime(d, e, p, m, ctx, NULL))
1145         return 0;
1146     if (!BN_mod_exp_simple(a, e, p, m, ctx))
1147         return 0;
1148     if (BN_cmp(a, d) != 0) {
1149         fprintf(stderr, "Modular exponentiation test failed!\n");
1150         return 0;
1151     }
1152     BN_MONT_CTX_free(mont);
1153     BN_free(a);
1154     BN_free(p);
1155     BN_free(m);
1156     BN_free(d);
1157     BN_free(e);
1158     return (1);
1159 }
1160
1161 int test_exp(BIO *bp, BN_CTX *ctx)
1162 {
1163     BIGNUM *a, *b, *d, *e, *one;
1164     int i;
1165
1166     a = BN_new();
1167     b = BN_new();
1168     d = BN_new();
1169     e = BN_new();
1170     one = BN_new();
1171     BN_one(one);
1172
1173     for (i = 0; i < num2; i++) {
1174         BN_bntest_rand(a, 20 + i * 5, 0, 0);
1175         BN_bntest_rand(b, 2 + i, 0, 0);
1176
1177         if (BN_exp(d, a, b, ctx) <= 0)
1178             return (0);
1179
1180         if (bp != NULL) {
1181             if (!results) {
1182                 BN_print(bp, a);
1183                 BIO_puts(bp, " ^ ");
1184                 BN_print(bp, b);
1185                 BIO_puts(bp, " - ");
1186             }
1187             BN_print(bp, d);
1188             BIO_puts(bp, "\n");
1189         }
1190         BN_one(e);
1191         for (; !BN_is_zero(b); BN_sub(b, b, one))
1192             BN_mul(e, e, a, ctx);
1193         BN_sub(e, e, d);
1194         if (!BN_is_zero(e)) {
1195             fprintf(stderr, "Exponentiation test failed!\n");
1196             return 0;
1197         }
1198     }
1199     BN_free(a);
1200     BN_free(b);
1201     BN_free(d);
1202     BN_free(e);
1203     BN_free(one);
1204     return (1);
1205 }
1206
1207 #ifndef OPENSSL_NO_EC2M
1208 int test_gf2m_add(BIO *bp)
1209 {
1210     BIGNUM a, b, c;
1211     int i, ret = 0;
1212
1213     BN_init(&a);
1214     BN_init(&b);
1215     BN_init(&c);
1216
1217     for (i = 0; i < num0; i++) {
1218         BN_rand(&a, 512, 0, 0);
1219         BN_copy(&b, BN_value_one());
1220         a.neg = rand_neg();
1221         b.neg = rand_neg();
1222         BN_GF2m_add(&c, &a, &b);
1223 # if 0                          /* make test uses ouput in bc but bc can't
1224                                  * handle GF(2^m) arithmetic */
1225         if (bp != NULL) {
1226             if (!results) {
1227                 BN_print(bp, &a);
1228                 BIO_puts(bp, " ^ ");
1229                 BN_print(bp, &b);
1230                 BIO_puts(bp, " = ");
1231             }
1232             BN_print(bp, &c);
1233             BIO_puts(bp, "\n");
1234         }
1235 # endif
1236         /* Test that two added values have the correct parity. */
1237         if ((BN_is_odd(&a) && BN_is_odd(&c))
1238             || (!BN_is_odd(&a) && !BN_is_odd(&c))) {
1239             fprintf(stderr, "GF(2^m) addition test (a) failed!\n");
1240             goto err;
1241         }
1242         BN_GF2m_add(&c, &c, &c);
1243         /* Test that c + c = 0. */
1244         if (!BN_is_zero(&c)) {
1245             fprintf(stderr, "GF(2^m) addition test (b) failed!\n");
1246             goto err;
1247         }
1248     }
1249     ret = 1;
1250  err:
1251     BN_free(&a);
1252     BN_free(&b);
1253     BN_free(&c);
1254     return ret;
1255 }
1256
1257 int test_gf2m_mod(BIO *bp)
1258 {
1259     BIGNUM *a, *b[2], *c, *d, *e;
1260     int i, j, ret = 0;
1261     int p0[] = { 163, 7, 6, 3, 0, -1 };
1262     int p1[] = { 193, 15, 0, -1 };
1263
1264     a = BN_new();
1265     b[0] = BN_new();
1266     b[1] = BN_new();
1267     c = BN_new();
1268     d = BN_new();
1269     e = BN_new();
1270
1271     BN_GF2m_arr2poly(p0, b[0]);
1272     BN_GF2m_arr2poly(p1, b[1]);
1273
1274     for (i = 0; i < num0; i++) {
1275         BN_bntest_rand(a, 1024, 0, 0);
1276         for (j = 0; j < 2; j++) {
1277             BN_GF2m_mod(c, a, b[j]);
1278 # if 0                          /* make test uses ouput in bc but bc can't
1279                                  * handle GF(2^m) arithmetic */
1280             if (bp != NULL) {
1281                 if (!results) {
1282                     BN_print(bp, a);
1283                     BIO_puts(bp, " % ");
1284                     BN_print(bp, b[j]);
1285                     BIO_puts(bp, " - ");
1286                     BN_print(bp, c);
1287                     BIO_puts(bp, "\n");
1288                 }
1289             }
1290 # endif
1291             BN_GF2m_add(d, a, c);
1292             BN_GF2m_mod(e, d, b[j]);
1293             /* Test that a + (a mod p) mod p == 0. */
1294             if (!BN_is_zero(e)) {
1295                 fprintf(stderr, "GF(2^m) modulo test failed!\n");
1296                 goto err;
1297             }
1298         }
1299     }
1300     ret = 1;
1301  err:
1302     BN_free(a);
1303     BN_free(b[0]);
1304     BN_free(b[1]);
1305     BN_free(c);
1306     BN_free(d);
1307     BN_free(e);
1308     return ret;
1309 }
1310
1311 int test_gf2m_mod_mul(BIO *bp, BN_CTX *ctx)
1312 {
1313     BIGNUM *a, *b[2], *c, *d, *e, *f, *g, *h;
1314     int i, j, ret = 0;
1315     int p0[] = { 163, 7, 6, 3, 0, -1 };
1316     int p1[] = { 193, 15, 0, -1 };
1317
1318     a = BN_new();
1319     b[0] = BN_new();
1320     b[1] = BN_new();
1321     c = BN_new();
1322     d = BN_new();
1323     e = BN_new();
1324     f = BN_new();
1325     g = BN_new();
1326     h = BN_new();
1327
1328     BN_GF2m_arr2poly(p0, b[0]);
1329     BN_GF2m_arr2poly(p1, b[1]);
1330
1331     for (i = 0; i < num0; i++) {
1332         BN_bntest_rand(a, 1024, 0, 0);
1333         BN_bntest_rand(c, 1024, 0, 0);
1334         BN_bntest_rand(d, 1024, 0, 0);
1335         for (j = 0; j < 2; j++) {
1336             BN_GF2m_mod_mul(e, a, c, b[j], ctx);
1337 # if 0                          /* make test uses ouput in bc but bc can't
1338                                  * handle GF(2^m) arithmetic */
1339             if (bp != NULL) {
1340                 if (!results) {
1341                     BN_print(bp, a);
1342                     BIO_puts(bp, " * ");
1343                     BN_print(bp, c);
1344                     BIO_puts(bp, " % ");
1345                     BN_print(bp, b[j]);
1346                     BIO_puts(bp, " - ");
1347                     BN_print(bp, e);
1348                     BIO_puts(bp, "\n");
1349                 }
1350             }
1351 # endif
1352             BN_GF2m_add(f, a, d);
1353             BN_GF2m_mod_mul(g, f, c, b[j], ctx);
1354             BN_GF2m_mod_mul(h, d, c, b[j], ctx);
1355             BN_GF2m_add(f, e, g);
1356             BN_GF2m_add(f, f, h);
1357             /* Test that (a+d)*c = a*c + d*c. */
1358             if (!BN_is_zero(f)) {
1359                 fprintf(stderr,
1360                         "GF(2^m) modular multiplication test failed!\n");
1361                 goto err;
1362             }
1363         }
1364     }
1365     ret = 1;
1366  err:
1367     BN_free(a);
1368     BN_free(b[0]);
1369     BN_free(b[1]);
1370     BN_free(c);
1371     BN_free(d);
1372     BN_free(e);
1373     BN_free(f);
1374     BN_free(g);
1375     BN_free(h);
1376     return ret;
1377 }
1378
1379 int test_gf2m_mod_sqr(BIO *bp, BN_CTX *ctx)
1380 {
1381     BIGNUM *a, *b[2], *c, *d;
1382     int i, j, ret = 0;
1383     int p0[] = { 163, 7, 6, 3, 0, -1 };
1384     int p1[] = { 193, 15, 0, -1 };
1385
1386     a = BN_new();
1387     b[0] = BN_new();
1388     b[1] = BN_new();
1389     c = BN_new();
1390     d = BN_new();
1391
1392     BN_GF2m_arr2poly(p0, b[0]);
1393     BN_GF2m_arr2poly(p1, b[1]);
1394
1395     for (i = 0; i < num0; i++) {
1396         BN_bntest_rand(a, 1024, 0, 0);
1397         for (j = 0; j < 2; j++) {
1398             BN_GF2m_mod_sqr(c, a, b[j], ctx);
1399             BN_copy(d, a);
1400             BN_GF2m_mod_mul(d, a, d, b[j], ctx);
1401 # if 0                          /* make test uses ouput in bc but bc can't
1402                                  * handle GF(2^m) arithmetic */
1403             if (bp != NULL) {
1404                 if (!results) {
1405                     BN_print(bp, a);
1406                     BIO_puts(bp, " ^ 2 % ");
1407                     BN_print(bp, b[j]);
1408                     BIO_puts(bp, " = ");
1409                     BN_print(bp, c);
1410                     BIO_puts(bp, "; a * a = ");
1411                     BN_print(bp, d);
1412                     BIO_puts(bp, "\n");
1413                 }
1414             }
1415 # endif
1416             BN_GF2m_add(d, c, d);
1417             /* Test that a*a = a^2. */
1418             if (!BN_is_zero(d)) {
1419                 fprintf(stderr, "GF(2^m) modular squaring test failed!\n");
1420                 goto err;
1421             }
1422         }
1423     }
1424     ret = 1;
1425  err:
1426     BN_free(a);
1427     BN_free(b[0]);
1428     BN_free(b[1]);
1429     BN_free(c);
1430     BN_free(d);
1431     return ret;
1432 }
1433
1434 int test_gf2m_mod_inv(BIO *bp, BN_CTX *ctx)
1435 {
1436     BIGNUM *a, *b[2], *c, *d;
1437     int i, j, ret = 0;
1438     int p0[] = { 163, 7, 6, 3, 0, -1 };
1439     int p1[] = { 193, 15, 0, -1 };
1440
1441     a = BN_new();
1442     b[0] = BN_new();
1443     b[1] = BN_new();
1444     c = BN_new();
1445     d = BN_new();
1446
1447     BN_GF2m_arr2poly(p0, b[0]);
1448     BN_GF2m_arr2poly(p1, b[1]);
1449
1450     for (i = 0; i < num0; i++) {
1451         BN_bntest_rand(a, 512, 0, 0);
1452         for (j = 0; j < 2; j++) {
1453             BN_GF2m_mod_inv(c, a, b[j], ctx);
1454             BN_GF2m_mod_mul(d, a, c, b[j], ctx);
1455 # if 0                          /* make test uses ouput in bc but bc can't
1456                                  * handle GF(2^m) arithmetic */
1457             if (bp != NULL) {
1458                 if (!results) {
1459                     BN_print(bp, a);
1460                     BIO_puts(bp, " * ");
1461                     BN_print(bp, c);
1462                     BIO_puts(bp, " - 1 % ");
1463                     BN_print(bp, b[j]);
1464                     BIO_puts(bp, "\n");
1465                 }
1466             }
1467 # endif
1468             /* Test that ((1/a)*a) = 1. */
1469             if (!BN_is_one(d)) {
1470                 fprintf(stderr, "GF(2^m) modular inversion test failed!\n");
1471                 goto err;
1472             }
1473         }
1474     }
1475     ret = 1;
1476  err:
1477     BN_free(a);
1478     BN_free(b[0]);
1479     BN_free(b[1]);
1480     BN_free(c);
1481     BN_free(d);
1482     return ret;
1483 }
1484
1485 int test_gf2m_mod_div(BIO *bp, BN_CTX *ctx)
1486 {
1487     BIGNUM *a, *b[2], *c, *d, *e, *f;
1488     int i, j, ret = 0;
1489     int p0[] = { 163, 7, 6, 3, 0, -1 };
1490     int p1[] = { 193, 15, 0, -1 };
1491
1492     a = BN_new();
1493     b[0] = BN_new();
1494     b[1] = BN_new();
1495     c = BN_new();
1496     d = BN_new();
1497     e = BN_new();
1498     f = BN_new();
1499
1500     BN_GF2m_arr2poly(p0, b[0]);
1501     BN_GF2m_arr2poly(p1, b[1]);
1502
1503     for (i = 0; i < num0; i++) {
1504         BN_bntest_rand(a, 512, 0, 0);
1505         BN_bntest_rand(c, 512, 0, 0);
1506         for (j = 0; j < 2; j++) {
1507             BN_GF2m_mod_div(d, a, c, b[j], ctx);
1508             BN_GF2m_mod_mul(e, d, c, b[j], ctx);
1509             BN_GF2m_mod_div(f, a, e, b[j], ctx);
1510 # if 0                          /* make test uses ouput in bc but bc can't
1511                                  * handle GF(2^m) arithmetic */
1512             if (bp != NULL) {
1513                 if (!results) {
1514                     BN_print(bp, a);
1515                     BIO_puts(bp, " = ");
1516                     BN_print(bp, c);
1517                     BIO_puts(bp, " * ");
1518                     BN_print(bp, d);
1519                     BIO_puts(bp, " % ");
1520                     BN_print(bp, b[j]);
1521                     BIO_puts(bp, "\n");
1522                 }
1523             }
1524 # endif
1525             /* Test that ((a/c)*c)/a = 1. */
1526             if (!BN_is_one(f)) {
1527                 fprintf(stderr, "GF(2^m) modular division test failed!\n");
1528                 goto err;
1529             }
1530         }
1531     }
1532     ret = 1;
1533  err:
1534     BN_free(a);
1535     BN_free(b[0]);
1536     BN_free(b[1]);
1537     BN_free(c);
1538     BN_free(d);
1539     BN_free(e);
1540     BN_free(f);
1541     return ret;
1542 }
1543
1544 int test_gf2m_mod_exp(BIO *bp, BN_CTX *ctx)
1545 {
1546     BIGNUM *a, *b[2], *c, *d, *e, *f;
1547     int i, j, ret = 0;
1548     int p0[] = { 163, 7, 6, 3, 0, -1 };
1549     int p1[] = { 193, 15, 0, -1 };
1550
1551     a = BN_new();
1552     b[0] = BN_new();
1553     b[1] = BN_new();
1554     c = BN_new();
1555     d = BN_new();
1556     e = BN_new();
1557     f = BN_new();
1558
1559     BN_GF2m_arr2poly(p0, b[0]);
1560     BN_GF2m_arr2poly(p1, b[1]);
1561
1562     for (i = 0; i < num0; i++) {
1563         BN_bntest_rand(a, 512, 0, 0);
1564         BN_bntest_rand(c, 512, 0, 0);
1565         BN_bntest_rand(d, 512, 0, 0);
1566         for (j = 0; j < 2; j++) {
1567             BN_GF2m_mod_exp(e, a, c, b[j], ctx);
1568             BN_GF2m_mod_exp(f, a, d, b[j], ctx);
1569             BN_GF2m_mod_mul(e, e, f, b[j], ctx);
1570             BN_add(f, c, d);
1571             BN_GF2m_mod_exp(f, a, f, b[j], ctx);
1572 # if 0                          /* make test uses ouput in bc but bc can't
1573                                  * handle GF(2^m) arithmetic */
1574             if (bp != NULL) {
1575                 if (!results) {
1576                     BN_print(bp, a);
1577                     BIO_puts(bp, " ^ (");
1578                     BN_print(bp, c);
1579                     BIO_puts(bp, " + ");
1580                     BN_print(bp, d);
1581                     BIO_puts(bp, ") = ");
1582                     BN_print(bp, e);
1583                     BIO_puts(bp, "; - ");
1584                     BN_print(bp, f);
1585                     BIO_puts(bp, " % ");
1586                     BN_print(bp, b[j]);
1587                     BIO_puts(bp, "\n");
1588                 }
1589             }
1590 # endif
1591             BN_GF2m_add(f, e, f);
1592             /* Test that a^(c+d)=a^c*a^d. */
1593             if (!BN_is_zero(f)) {
1594                 fprintf(stderr,
1595                         "GF(2^m) modular exponentiation test failed!\n");
1596                 goto err;
1597             }
1598         }
1599     }
1600     ret = 1;
1601  err:
1602     BN_free(a);
1603     BN_free(b[0]);
1604     BN_free(b[1]);
1605     BN_free(c);
1606     BN_free(d);
1607     BN_free(e);
1608     BN_free(f);
1609     return ret;
1610 }
1611
1612 int test_gf2m_mod_sqrt(BIO *bp, BN_CTX *ctx)
1613 {
1614     BIGNUM *a, *b[2], *c, *d, *e, *f;
1615     int i, j, ret = 0;
1616     int p0[] = { 163, 7, 6, 3, 0, -1 };
1617     int p1[] = { 193, 15, 0, -1 };
1618
1619     a = BN_new();
1620     b[0] = BN_new();
1621     b[1] = BN_new();
1622     c = BN_new();
1623     d = BN_new();
1624     e = BN_new();
1625     f = BN_new();
1626
1627     BN_GF2m_arr2poly(p0, b[0]);
1628     BN_GF2m_arr2poly(p1, b[1]);
1629
1630     for (i = 0; i < num0; i++) {
1631         BN_bntest_rand(a, 512, 0, 0);
1632         for (j = 0; j < 2; j++) {
1633             BN_GF2m_mod(c, a, b[j]);
1634             BN_GF2m_mod_sqrt(d, a, b[j], ctx);
1635             BN_GF2m_mod_sqr(e, d, b[j], ctx);
1636 # if 0                          /* make test uses ouput in bc but bc can't
1637                                  * handle GF(2^m) arithmetic */
1638             if (bp != NULL) {
1639                 if (!results) {
1640                     BN_print(bp, d);
1641                     BIO_puts(bp, " ^ 2 - ");
1642                     BN_print(bp, a);
1643                     BIO_puts(bp, "\n");
1644                 }
1645             }
1646 # endif
1647             BN_GF2m_add(f, c, e);
1648             /* Test that d^2 = a, where d = sqrt(a). */
1649             if (!BN_is_zero(f)) {
1650                 fprintf(stderr, "GF(2^m) modular square root test failed!\n");
1651                 goto err;
1652             }
1653         }
1654     }
1655     ret = 1;
1656  err:
1657     BN_free(a);
1658     BN_free(b[0]);
1659     BN_free(b[1]);
1660     BN_free(c);
1661     BN_free(d);
1662     BN_free(e);
1663     BN_free(f);
1664     return ret;
1665 }
1666
1667 int test_gf2m_mod_solve_quad(BIO *bp, BN_CTX *ctx)
1668 {
1669     BIGNUM *a, *b[2], *c, *d, *e;
1670     int i, j, s = 0, t, ret = 0;
1671     int p0[] = { 163, 7, 6, 3, 0, -1 };
1672     int p1[] = { 193, 15, 0, -1 };
1673
1674     a = BN_new();
1675     b[0] = BN_new();
1676     b[1] = BN_new();
1677     c = BN_new();
1678     d = BN_new();
1679     e = BN_new();
1680
1681     BN_GF2m_arr2poly(p0, b[0]);
1682     BN_GF2m_arr2poly(p1, b[1]);
1683
1684     for (i = 0; i < num0; i++) {
1685         BN_bntest_rand(a, 512, 0, 0);
1686         for (j = 0; j < 2; j++) {
1687             t = BN_GF2m_mod_solve_quad(c, a, b[j], ctx);
1688             if (t) {
1689                 s++;
1690                 BN_GF2m_mod_sqr(d, c, b[j], ctx);
1691                 BN_GF2m_add(d, c, d);
1692                 BN_GF2m_mod(e, a, b[j]);
1693 # if 0                          /* make test uses ouput in bc but bc can't
1694                                  * handle GF(2^m) arithmetic */
1695                 if (bp != NULL) {
1696                     if (!results) {
1697                         BN_print(bp, c);
1698                         BIO_puts(bp, " is root of z^2 + z = ");
1699                         BN_print(bp, a);
1700                         BIO_puts(bp, " % ");
1701                         BN_print(bp, b[j]);
1702                         BIO_puts(bp, "\n");
1703                     }
1704                 }
1705 # endif
1706                 BN_GF2m_add(e, e, d);
1707                 /*
1708                  * Test that solution of quadratic c satisfies c^2 + c = a.
1709                  */
1710                 if (!BN_is_zero(e)) {
1711                     fprintf(stderr,
1712                             "GF(2^m) modular solve quadratic test failed!\n");
1713                     goto err;
1714                 }
1715
1716             } else {
1717 # if 0                          /* make test uses ouput in bc but bc can't
1718                                  * handle GF(2^m) arithmetic */
1719                 if (bp != NULL) {
1720                     if (!results) {
1721                         BIO_puts(bp, "There are no roots of z^2 + z = ");
1722                         BN_print(bp, a);
1723                         BIO_puts(bp, " % ");
1724                         BN_print(bp, b[j]);
1725                         BIO_puts(bp, "\n");
1726                     }
1727                 }
1728 # endif
1729             }
1730         }
1731     }
1732     if (s == 0) {
1733         fprintf(stderr,
1734                 "All %i tests of GF(2^m) modular solve quadratic resulted in no roots;\n",
1735                 num0);
1736         fprintf(stderr,
1737                 "this is very unlikely and probably indicates an error.\n");
1738         goto err;
1739     }
1740     ret = 1;
1741  err:
1742     BN_free(a);
1743     BN_free(b[0]);
1744     BN_free(b[1]);
1745     BN_free(c);
1746     BN_free(d);
1747     BN_free(e);
1748     return ret;
1749 }
1750 #endif
1751 static int genprime_cb(int p, int n, BN_GENCB *arg)
1752 {
1753     char c = '*';
1754
1755     if (p == 0)
1756         c = '.';
1757     if (p == 1)
1758         c = '+';
1759     if (p == 2)
1760         c = '*';
1761     if (p == 3)
1762         c = '\n';
1763     putc(c, stderr);
1764     fflush(stderr);
1765     return 1;
1766 }
1767
1768 int test_kron(BIO *bp, BN_CTX *ctx)
1769 {
1770     BN_GENCB cb;
1771     BIGNUM *a, *b, *r, *t;
1772     int i;
1773     int legendre, kronecker;
1774     int ret = 0;
1775
1776     a = BN_new();
1777     b = BN_new();
1778     r = BN_new();
1779     t = BN_new();
1780     if (a == NULL || b == NULL || r == NULL || t == NULL)
1781         goto err;
1782
1783     BN_GENCB_set(&cb, genprime_cb, NULL);
1784
1785     /*
1786      * We test BN_kronecker(a, b, ctx) just for b odd (Jacobi symbol). In
1787      * this case we know that if b is prime, then BN_kronecker(a, b, ctx) is
1788      * congruent to $a^{(b-1)/2}$, modulo $b$ (Legendre symbol). So we
1789      * generate a random prime b and compare these values for a number of
1790      * random a's.  (That is, we run the Solovay-Strassen primality test to
1791      * confirm that b is prime, except that we don't want to test whether b
1792      * is prime but whether BN_kronecker works.)
1793      */
1794
1795     if (!BN_generate_prime_ex(b, 512, 0, NULL, NULL, &cb))
1796         goto err;
1797     b->neg = rand_neg();
1798     putc('\n', stderr);
1799
1800     for (i = 0; i < num0; i++) {
1801         if (!BN_bntest_rand(a, 512, 0, 0))
1802             goto err;
1803         a->neg = rand_neg();
1804
1805         /* t := (|b|-1)/2  (note that b is odd) */
1806         if (!BN_copy(t, b))
1807             goto err;
1808         t->neg = 0;
1809         if (!BN_sub_word(t, 1))
1810             goto err;
1811         if (!BN_rshift1(t, t))
1812             goto err;
1813         /* r := a^t mod b */
1814         b->neg = 0;
1815
1816         if (!BN_mod_exp_recp(r, a, t, b, ctx))
1817             goto err;
1818         b->neg = 1;
1819
1820         if (BN_is_word(r, 1))
1821             legendre = 1;
1822         else if (BN_is_zero(r))
1823             legendre = 0;
1824         else {
1825             if (!BN_add_word(r, 1))
1826                 goto err;
1827             if (0 != BN_ucmp(r, b)) {
1828                 fprintf(stderr, "Legendre symbol computation failed\n");
1829                 goto err;
1830             }
1831             legendre = -1;
1832         }
1833
1834         kronecker = BN_kronecker(a, b, ctx);
1835         if (kronecker < -1)
1836             goto err;
1837         /* we actually need BN_kronecker(a, |b|) */
1838         if (a->neg && b->neg)
1839             kronecker = -kronecker;
1840
1841         if (legendre != kronecker) {
1842             fprintf(stderr, "legendre != kronecker; a = ");
1843             BN_print_fp(stderr, a);
1844             fprintf(stderr, ", b = ");
1845             BN_print_fp(stderr, b);
1846             fprintf(stderr, "\n");
1847             goto err;
1848         }
1849
1850         putc('.', stderr);
1851         fflush(stderr);
1852     }
1853
1854     putc('\n', stderr);
1855     fflush(stderr);
1856     ret = 1;
1857  err:
1858     if (a != NULL)
1859         BN_free(a);
1860     if (b != NULL)
1861         BN_free(b);
1862     if (r != NULL)
1863         BN_free(r);
1864     if (t != NULL)
1865         BN_free(t);
1866     return ret;
1867 }
1868
1869 int test_sqrt(BIO *bp, BN_CTX *ctx)
1870 {
1871     BN_GENCB cb;
1872     BIGNUM *a, *p, *r;
1873     int i, j;
1874     int ret = 0;
1875
1876     a = BN_new();
1877     p = BN_new();
1878     r = BN_new();
1879     if (a == NULL || p == NULL || r == NULL)
1880         goto err;
1881
1882     BN_GENCB_set(&cb, genprime_cb, NULL);
1883
1884     for (i = 0; i < 16; i++) {
1885         if (i < 8) {
1886             unsigned primes[8] = { 2, 3, 5, 7, 11, 13, 17, 19 };
1887
1888             if (!BN_set_word(p, primes[i]))
1889                 goto err;
1890         } else {
1891             if (!BN_set_word(a, 32))
1892                 goto err;
1893             if (!BN_set_word(r, 2 * i + 1))
1894                 goto err;
1895
1896             if (!BN_generate_prime_ex(p, 256, 0, a, r, &cb))
1897                 goto err;
1898             putc('\n', stderr);
1899         }
1900         p->neg = rand_neg();
1901
1902         for (j = 0; j < num2; j++) {
1903             /*
1904              * construct 'a' such that it is a square modulo p, but in
1905              * general not a proper square and not reduced modulo p
1906              */
1907             if (!BN_bntest_rand(r, 256, 0, 3))
1908                 goto err;
1909             if (!BN_nnmod(r, r, p, ctx))
1910                 goto err;
1911             if (!BN_mod_sqr(r, r, p, ctx))
1912                 goto err;
1913             if (!BN_bntest_rand(a, 256, 0, 3))
1914                 goto err;
1915             if (!BN_nnmod(a, a, p, ctx))
1916                 goto err;
1917             if (!BN_mod_sqr(a, a, p, ctx))
1918                 goto err;
1919             if (!BN_mul(a, a, r, ctx))
1920                 goto err;
1921             if (rand_neg())
1922                 if (!BN_sub(a, a, p))
1923                     goto err;
1924
1925             if (!BN_mod_sqrt(r, a, p, ctx))
1926                 goto err;
1927             if (!BN_mod_sqr(r, r, p, ctx))
1928                 goto err;
1929
1930             if (!BN_nnmod(a, a, p, ctx))
1931                 goto err;
1932
1933             if (BN_cmp(a, r) != 0) {
1934                 fprintf(stderr, "BN_mod_sqrt failed: a = ");
1935                 BN_print_fp(stderr, a);
1936                 fprintf(stderr, ", r = ");
1937                 BN_print_fp(stderr, r);
1938                 fprintf(stderr, ", p = ");
1939                 BN_print_fp(stderr, p);
1940                 fprintf(stderr, "\n");
1941                 goto err;
1942             }
1943
1944             putc('.', stderr);
1945             fflush(stderr);
1946         }
1947
1948         putc('\n', stderr);
1949         fflush(stderr);
1950     }
1951     ret = 1;
1952  err:
1953     if (a != NULL)
1954         BN_free(a);
1955     if (p != NULL)
1956         BN_free(p);
1957     if (r != NULL)
1958         BN_free(r);
1959     return ret;
1960 }
1961
1962 int test_lshift(BIO *bp, BN_CTX *ctx, BIGNUM *a_)
1963 {
1964     BIGNUM *a, *b, *c, *d;
1965     int i;
1966
1967     b = BN_new();
1968     c = BN_new();
1969     d = BN_new();
1970     BN_one(c);
1971
1972     if (a_)
1973         a = a_;
1974     else {
1975         a = BN_new();
1976         BN_bntest_rand(a, 200, 0, 0);
1977         a->neg = rand_neg();
1978     }
1979     for (i = 0; i < num0; i++) {
1980         BN_lshift(b, a, i + 1);
1981         BN_add(c, c, c);
1982         if (bp != NULL) {
1983             if (!results) {
1984                 BN_print(bp, a);
1985                 BIO_puts(bp, " * ");
1986                 BN_print(bp, c);
1987                 BIO_puts(bp, " - ");
1988             }
1989             BN_print(bp, b);
1990             BIO_puts(bp, "\n");
1991         }
1992         BN_mul(d, a, c, ctx);
1993         BN_sub(d, d, b);
1994         if (!BN_is_zero(d)) {
1995             fprintf(stderr, "Left shift test failed!\n");
1996             fprintf(stderr, "a=");
1997             BN_print_fp(stderr, a);
1998             fprintf(stderr, "\nb=");
1999             BN_print_fp(stderr, b);
2000             fprintf(stderr, "\nc=");
2001             BN_print_fp(stderr, c);
2002             fprintf(stderr, "\nd=");
2003             BN_print_fp(stderr, d);
2004             fprintf(stderr, "\n");
2005             return 0;
2006         }
2007     }
2008     BN_free(a);
2009     BN_free(b);
2010     BN_free(c);
2011     BN_free(d);
2012     return (1);
2013 }
2014
2015 int test_lshift1(BIO *bp)
2016 {
2017     BIGNUM *a, *b, *c;
2018     int i;
2019
2020     a = BN_new();
2021     b = BN_new();
2022     c = BN_new();
2023
2024     BN_bntest_rand(a, 200, 0, 0);
2025     a->neg = rand_neg();
2026     for (i = 0; i < num0; i++) {
2027         BN_lshift1(b, a);
2028         if (bp != NULL) {
2029             if (!results) {
2030                 BN_print(bp, a);
2031                 BIO_puts(bp, " * 2");
2032                 BIO_puts(bp, " - ");
2033             }
2034             BN_print(bp, b);
2035             BIO_puts(bp, "\n");
2036         }
2037         BN_add(c, a, a);
2038         BN_sub(a, b, c);
2039         if (!BN_is_zero(a)) {
2040             fprintf(stderr, "Left shift one test failed!\n");
2041             return 0;
2042         }
2043
2044         BN_copy(a, b);
2045     }
2046     BN_free(a);
2047     BN_free(b);
2048     BN_free(c);
2049     return (1);
2050 }
2051
2052 int test_rshift(BIO *bp, BN_CTX *ctx)
2053 {
2054     BIGNUM *a, *b, *c, *d, *e;
2055     int i;
2056
2057     a = BN_new();
2058     b = BN_new();
2059     c = BN_new();
2060     d = BN_new();
2061     e = BN_new();
2062     BN_one(c);
2063
2064     BN_bntest_rand(a, 200, 0, 0);
2065     a->neg = rand_neg();
2066     for (i = 0; i < num0; i++) {
2067         BN_rshift(b, a, i + 1);
2068         BN_add(c, c, c);
2069         if (bp != NULL) {
2070             if (!results) {
2071                 BN_print(bp, a);
2072                 BIO_puts(bp, " / ");
2073                 BN_print(bp, c);
2074                 BIO_puts(bp, " - ");
2075             }
2076             BN_print(bp, b);
2077             BIO_puts(bp, "\n");
2078         }
2079         BN_div(d, e, a, c, ctx);
2080         BN_sub(d, d, b);
2081         if (!BN_is_zero(d)) {
2082             fprintf(stderr, "Right shift test failed!\n");
2083             return 0;
2084         }
2085     }
2086     BN_free(a);
2087     BN_free(b);
2088     BN_free(c);
2089     BN_free(d);
2090     BN_free(e);
2091     return (1);
2092 }
2093
2094 int test_rshift1(BIO *bp)
2095 {
2096     BIGNUM *a, *b, *c;
2097     int i;
2098
2099     a = BN_new();
2100     b = BN_new();
2101     c = BN_new();
2102
2103     BN_bntest_rand(a, 200, 0, 0);
2104     a->neg = rand_neg();
2105     for (i = 0; i < num0; i++) {
2106         BN_rshift1(b, a);
2107         if (bp != NULL) {
2108             if (!results) {
2109                 BN_print(bp, a);
2110                 BIO_puts(bp, " / 2");
2111                 BIO_puts(bp, " - ");
2112             }
2113             BN_print(bp, b);
2114             BIO_puts(bp, "\n");
2115         }
2116         BN_sub(c, a, b);
2117         BN_sub(c, c, b);
2118         if (!BN_is_zero(c) && !BN_abs_is_word(c, 1)) {
2119             fprintf(stderr, "Right shift one test failed!\n");
2120             return 0;
2121         }
2122         BN_copy(a, b);
2123     }
2124     BN_free(a);
2125     BN_free(b);
2126     BN_free(c);
2127     return (1);
2128 }
2129
2130 int rand_neg(void)
2131 {
2132     static unsigned int neg = 0;
2133     static int sign[8] = { 0, 0, 0, 1, 1, 0, 1, 1 };
2134
2135     return (sign[(neg++) % 8]);
2136 }