1 /* $OpenBSD: bn.h,v 1.43 2021/09/10 14:33:44 tb Exp $ */
2 /* Copyright (C) 1995-1997 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 core.stdc.config.c_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 (c) 1998-2006 The OpenSSL Project.  All rights reserved.
60  *
61  * Redistribution and use in source and binary forms, with or without
62  * modification, are permitted provided that the following conditions
63  * are met:
64  *
65  * 1. Redistributions of source code must retain the above copyright
66  *    notice, this list of conditions and the following disclaimer.
67  *
68  * 2. Redistributions in binary form must reproduce the above copyright
69  *    notice, this list of conditions and the following disclaimer in
70  *    the documentation and/or other materials provided with the
71  *    distribution.
72  *
73  * 3. All advertising materials mentioning features or use of this
74  *    software must display the following acknowledgment:
75  *    "This product includes software developed by the OpenSSL Project
76  *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
77  *
78  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
79  *    endorse or promote products derived from this software without
80  *    prior written permission. For written permission, please contact
81  *    openssl-core@openssl.org.
82  *
83  * 5. Products derived from this software may not be called "OpenSSL"
84  *    nor may "OpenSSL" appear in their names without prior written
85  *    permission of the OpenSSL Project.
86  *
87  * 6. Redistributions of any form whatsoever must retain the following
88  *    acknowledgment:
89  *    "This product includes software developed by the OpenSSL Project
90  *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
91  *
92  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
93  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
94  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
95  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
96  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
97  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
98  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
99  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
100  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
101  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
102  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
103  * OF THE POSSIBILITY OF SUCH DAMAGE.
104  * ====================================================================
105  *
106  * This product includes cryptographic software written by Eric Young
107  * (eay@cryptsoft.com).  This product includes software written by Tim
108  * Hudson (tjh@cryptsoft.com).
109  *
110  */
111 /* ====================================================================
112  * Copyright 2002 Sun Microsystems, Inc. ALL RIGHTS RESERVED.
113  *
114  * Portions of the attached software ("Contribution") are developed by
115  * SUN MICROSYSTEMS, INC., and are contributed to the OpenSSL project.
116  *
117  * The Contribution is licensed pursuant to the Eric Young open source
118  * license provided above.
119  *
120  * The binary polynomial arithmetic software is originally written by
121  * Sheueling Chang Shantz and Douglas Stebila of Sun Microsystems Laboratories.
122  *
123  */
124 module libressl_d.openssl.bn;
125 
126 
127 private static import core.stdc.config;
128 public import libressl_d.compat.stdio;
129 public import libressl_d.compat.stdlib;
130 public import libressl_d.openssl.bio;
131 public import libressl_d.openssl.crypto;
132 public import libressl_d.openssl.opensslconf;
133 public import libressl_d.openssl.ossl_typ;
134 
135 enum HEADER_BN_H = true;
136 
137 extern (C):
138 nothrow @nogc:
139 
140 /*
141  * These preprocessor symbols control various aspects of the bignum headers and
142  * library code. They're not defined by any "normal" configuration, as they are
143  * intended for development and testing purposes. NB: defining all three can be
144  * useful for debugging application code as well as openssl itself.
145  *
146  * BN_DEBUG - turn on various debugging alterations to the bignum code
147  * BN_DEBUG_RAND - uses random poisoning of unused words to trip up
148  * mismanagement of bignum internals. You must also define BN_DEBUG.
149  */
150 /* version = BN_DEBUG; */
151 /* version = BN_DEBUG_RAND; */
152 
153 version (OPENSSL_SMALL_FOOTPRINT) {
154 } else {
155 	//#define BN_MUL_COMBA
156 	//#define BN_SQR_COMBA
157 	//#define BN_RECURSION
158 }
159 
160 /*
161  * This next option uses the C libraries (2 word)/(1 word) function.
162  * If it is not defined, I use my C version (which is slower).
163  * The reason for this flag is that when the particular C compiler
164  * library routine is used, and the library is linked with a different
165  * compiler, the library is missing.  This mostly happens when the
166  * library is built with gcc and then linked using normal cc.  This would
167  * be a common occurrence because gcc normally produces code that is
168  * 2 times faster than system compilers for the big number stuff.
169  * For machines with only one compiler (or shared libraries), this should
170  * be on.  Again this in only really a problem on machines
171  * using "long long's", are 32bit, and are not using my assembler code.
172  */
173 /* version = BN_DIV2W; */
174 
175 //ToDo:
176 version (Windows) {
177 } else {
178 	version (D_LP64) {
179 		version = C_LP64;
180 	}
181 }
182 
183 //#if defined(_LP64)
184 version (C_LP64) {
185 	//#undef BN_LLONG
186 	alias BN_ULONG = core.stdc.config.c_ulong;
187 	alias BN_LONG = core.stdc.config.c_long;
188 	enum BN_BITS = 128;
189 	enum BN_BYTES = 8;
190 	enum BN_BITS2 = 64;
191 	enum BN_BITS4 = 32;
192 	enum BN_MASK2 = 0xFFFFFFFFFFFFFFFFL;
193 	enum BN_MASK2l = 0xFFFFFFFFL;
194 	enum BN_MASK2h = 0xFFFFFFFF00000000L;
195 	enum BN_MASK2h1 = 0xFFFFFFFF80000000L;
196 	enum BN_TBIT = 0x8000000000000000L;
197 	enum BN_DEC_CONV = 10000000000000000000UL;
198 	enum BN_DEC_FMT1 = "%lu";
199 	enum BN_DEC_FMT2 = "%019lu";
200 	enum BN_DEC_NUM = 19;
201 	enum BN_HEX_FMT1 = "%lX";
202 	enum BN_HEX_FMT2 = "%016lX";
203 } else {
204 	alias BN_ULLONG = core.stdc.config.cpp_ulonglong;
205 	//#define BN_LLONG
206 	alias BN_ULONG = uint;
207 	alias BN_LONG = int;
208 	enum BN_BITS = 64;
209 	enum BN_BYTES = 4;
210 	enum BN_BITS2 = 32;
211 	enum BN_BITS4 = 16;
212 	enum BN_MASK = 0xFFFFFFFFFFFFFFFFL;
213 	enum BN_MASK2 = 0xFFFFFFFFL;
214 	enum BN_MASK2l = 0xFFFF;
215 	enum BN_MASK2h1 = 0xFFFF8000L;
216 	enum BN_MASK2h = 0xFFFF0000L;
217 	enum BN_TBIT = 0x80000000L;
218 	enum BN_DEC_CONV = 1000000000L;
219 	enum BN_DEC_FMT1 = "%u";
220 	enum BN_DEC_FMT2 = "%09u";
221 	enum BN_DEC_NUM = 9;
222 	enum BN_HEX_FMT1 = "%X";
223 	enum BN_HEX_FMT2 = "%08X";
224 }
225 
226 enum BN_FLG_MALLOCED = 0x01;
227 enum BN_FLG_STATIC_DATA = 0x02;
228 
229 /**
230  * avoid leaking exponent information through timing,
231  * BN_mod_exp_mont() will call BN_mod_exp_mont_consttime,
232  * BN_div() will call BN_div_no_branch,
233  * BN_mod_inverse() will call BN_mod_inverse_no_branch.
234  */
235 enum BN_FLG_CONSTTIME = 0x04;
236 
237 version (OPENSSL_NO_DEPRECATED) {
238 } else {
239 	/**
240 	 * deprecated name for the flag
241 	 */
242 	enum BN_FLG_EXP_CONSTTIME = .BN_FLG_CONSTTIME;
243 
244 	/*
245 	 * avoid leaking exponent information through timings
246 	 * (BN_mod_exp_mont() will call BN_mod_exp_mont_consttime)
247 	 */
248 }
249 
250 version (OPENSSL_NO_DEPRECATED) {
251 } else {
252 	/**
253 	 * used for debuging
254 	 */
255 	enum BN_FLG_FREE = 0x8000;
256 }
257 
258 pragma(inline, true)
259 pure nothrow @trusted @nogc @live
260 void BN_set_flags(B, N)(scope B* b, N n)
261 
262 	in
263 	{
264 		assert(b != null);
265 	}
266 
267 	do
268 	{
269 		b.flags |= n;
270 	}
271 
272 pragma(inline, true)
273 pure nothrow @trusted @nogc @live
274 auto BN_get_flags(B, N)(scope const B* b, N n)
275 
276 	in
277 	{
278 		assert(b != null);
279 	}
280 
281 	do
282 	{
283 		return b.flags & n;
284 	}
285 
286 /**
287  * Values for |top| in BN_rand()
288  */
289 enum BN_RAND_TOP_ANY = -1;
290 
291 ///Ditto
292 enum BN_RAND_TOP_ONE = 0;
293 
294 ///Ditto
295 enum BN_RAND_TOP_TWO = 1;
296 
297 /**
298  * Values for |bottom| in BN_rand()
299  */
300 enum BN_RAND_BOTTOM_ANY = 0;
301 
302 ///Ditto
303 enum BN_RAND_BOTTOM_ODD = 1;
304 
305 /**
306  * get a clone of a BIGNUM with changed flags, for *temporary* use only
307  * (the two BIGNUMs cannot not be used in parallel!)
308  */
309 pragma(inline, true)
310 pure nothrow @trusted @nogc @live
311 void BN_with_flags(scope libressl_d.openssl.ossl_typ.BIGNUM* dest, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, int n)
312 
313 	in
314 	{
315 		assert(dest != null);
316 		assert(b != null);
317 	}
318 
319 	do
320 	{
321 		dest.d = cast(.BN_ULONG*)(b.d);
322 		dest.top = b.top;
323 		dest.dmax = b.dmax;
324 		dest.neg = b.neg;
325 		dest.flags = (dest.flags & .BN_FLG_MALLOCED) | (b.flags & ~.BN_FLG_MALLOCED) | (.BN_FLG_STATIC_DATA) | (n);
326 	}
327 
328 struct bignum_st
329 {
330 	/**
331 	 * Pointer to an array of 'BN_BITS2' bit chunks.
332 	 */
333 	.BN_ULONG* d;
334 
335 	/**
336 	 * Index of last used d +1.
337 	 */
338 	int top;
339 
340 	/* The next are internal book keeping for bn_expand. */
341 
342 	/**
343 	 * Size of the d array.
344 	 */
345 	int dmax;
346 
347 	/**
348 	 * one if the number is negative
349 	 */
350 	int neg;
351 
352 	int flags;
353 }
354 
355 /**
356  * Used for montgomery multiplication
357  */
358 struct bn_mont_ctx_st
359 {
360 	/**
361 	 * number of bits in R
362 	 */
363 	int ri;
364 
365 	/**
366 	 * used to convert to montgomery form
367 	 */
368 	libressl_d.openssl.ossl_typ.BIGNUM RR;
369 
370 	/**
371 	 * The modulus
372 	 */
373 	libressl_d.openssl.ossl_typ.BIGNUM N;
374 
375 	/**
376 	 * R*(1/R mod N) - N*Ni = 1
377 	 * (Ni is only stored for bignum algorithm)
378 	 */
379 	libressl_d.openssl.ossl_typ.BIGNUM Ni;
380 
381 	/**
382 	 * least significant word(s) of Ni;
383 	 * (type changed with 0.9.9, was "BN_ULONG n0;" before)
384 	 */
385 	.BN_ULONG[2] n0;
386 
387 	int flags;
388 }
389 
390 /**
391  * Used for reciprocal division/mod functions
392  * It cannot be shared between threads
393  */
394 struct bn_recp_ctx_st
395 {
396 	/**
397 	 * the divisor
398 	 */
399 	libressl_d.openssl.ossl_typ.BIGNUM N;
400 
401 	/**
402 	 * the reciprocal
403 	 */
404 	libressl_d.openssl.ossl_typ.BIGNUM Nr;
405 
406 	int num_bits;
407 	int shift;
408 	int flags;
409 }
410 
411 /**
412  * Used for slow "generation" functions.
413  */
414 struct bn_gencb_st
415 {
416 	/**
417 	 * To handle binary (in)compatibility
418 	 */
419 	uint ver;
420 
421 	/**
422 	 * callback-specific data
423 	 */
424 	void* arg;
425 
426 	union cb_
427 	{
428 		/**
429 		 * if(ver==1) - handles old style callbacks
430 		 */
431 		void function(int, int, void*) cb_1;
432 
433 		/**
434 		 * if(ver==2) - new callback style
435 		 */
436 		int function(int, int, libressl_d.openssl.ossl_typ.BN_GENCB*) cb_2;
437 	}
438 
439 	cb_ cb;
440 }
441 
442 libressl_d.openssl.ossl_typ.BN_GENCB* BN_GENCB_new();
443 void BN_GENCB_free(libressl_d.openssl.ossl_typ.BN_GENCB* cb);
444 void* BN_GENCB_get_arg(libressl_d.openssl.ossl_typ.BN_GENCB* cb);
445 
446 /**
447  * Wrapper function to make using BN_GENCB easier,
448  */
449 int BN_GENCB_call(libressl_d.openssl.ossl_typ.BN_GENCB* cb, int a, int b);
450 
451 /*
452  * Macro to populate a BN_GENCB structure with an "old"-style callback
453  */
454 pragma(inline, true)
455 pure nothrow @trusted @nogc @live
456 void BN_GENCB_set_old(scope libressl_d.openssl.ossl_typ.BN_GENCB* gencb, void function(int, int, void*) callback, void* cb_arg)
457 
458 	in
459 	{
460 		assert(gencb != null);
461 	}
462 
463 	do
464 	{
465 		libressl_d.openssl.ossl_typ.BN_GENCB* tmp_gencb = gencb;
466 		tmp_gencb.ver = 1;
467 		tmp_gencb.arg = cb_arg;
468 		tmp_gencb.cb.cb_1 = callback;
469 	}
470 
471 /*
472  * Macro to populate a BN_GENCB structure with a "new"-style callback
473  */
474 pragma(inline, true)
475 pure nothrow @trusted @nogc @live
476 void BN_GENCB_set(scope libressl_d.openssl.ossl_typ.BN_GENCB* gencb, int function(int, int, libressl_d.openssl.ossl_typ.BN_GENCB*) callback, void* cb_arg)
477 
478 	in
479 	{
480 		assert(gencb != null);
481 	}
482 
483 	do
484 	{
485 		libressl_d.openssl.ossl_typ.BN_GENCB* tmp_gencb = gencb;
486 		tmp_gencb.ver = 2;
487 		tmp_gencb.arg = cb_arg;
488 		tmp_gencb.cb.cb_2 = callback;
489 	}
490 
491 /**
492  * default: select number of iterations
493  * based on the size of the number
494  */
495 enum BN_prime_checks = 0;
496 
497 /*
498  * BN_prime_checks_for_size() returns the number of Miller-Rabin
499  * iterations that will be done for checking that a random number
500  * is probably prime.  The error rate for accepting a composite
501  * number as prime depends on the size of the prime |b|.  The error
502  * rates used are for calculating an RSA key with 2 primes, and so
503  * the level is what you would expect for a key of double the size
504  * of the prime.
505  *
506  * This table is generated using the algorithm of FIPS PUB 186-4
507  * Digital Signature Standard (DSS), section F.1, page 117.
508  * (https://dx.doi.org/10.6028/NIST.FIPS.186-4)
509  *
510  * The following magma script was used to generate the output:
511  * securitybits:=125;
512  * k:=1024;
513  * for t:=1 to 65 do
514  *   for M:=3 to Floor(2*Sqrt(k-1)-1) do
515  *     S:=0;
516  *     // Sum over m
517  *     for m:=3 to M do
518  *       s:=0;
519  *       // Sum over j
520  *       for j:=2 to m do
521  *         s+:=(RealField(32)!2)^-(j+(k-1)/j);
522  *       end for;
523  *       S+:=2^(m-(m-1)*t)*s;
524  *     end for;
525  *     A:=2^(k-2-M*t);
526  *     B:=8*(Pi(RealField(32))^2-6)/3*2^(k-2)*S;
527  *     pkt:=2.00743*Log(2)*k*2^-k*(A+B);
528  *     seclevel:=Floor(-Log(2,pkt));
529  *     if seclevel ge securitybits then
530  *       printf "k: %5o, security: %o bits  (t: %o, M: %o)\n",k,seclevel,t,M;
531  *       break;
532  *     end if;
533  *   end for;
534  *   if seclevel ge securitybits then break; end if;
535  * end for;
536  *
537  * It can be run online at:
538  * http://magma.maths.usyd.edu.au/calc
539  *
540  * And will output:
541  * k:  1024, security: 129 bits  (t: 6, M: 23)
542  *
543  * k is the number of bits of the prime, securitybits is the level
544  * we want to reach.
545  *
546  * prime length | RSA key size | # MR tests | security level
547  * -------------+--------------|------------+---------------
548  *  (b) >= 6394 |     >= 12788 |          3 |        256 bit
549  *  (b) >= 3747 |     >=  7494 |          3 |        192 bit
550  *  (b) >= 1345 |     >=  2690 |          4 |        128 bit
551  *  (b) >= 1080 |     >=  2160 |          5 |        128 bit
552  *  (b) >=  852 |     >=  1704 |          5 |        112 bit
553  *  (b) >=  476 |     >=   952 |          5 |         80 bit
554  *  (b) >=  400 |     >=   800 |          6 |         80 bit
555  *  (b) >=  347 |     >=   694 |          7 |         80 bit
556  *  (b) >=  308 |     >=   616 |          8 |         80 bit
557  *  (b) >=   55 |     >=   110 |         27 |         64 bit
558  *  (b) >=    6 |     >=    12 |         34 |         64 bit
559  */
560 
561 pragma(inline, true)
562 pure nothrow @safe @nogc @live
563 int BN_prime_checks_for_size(B)(B b)
564 	if (B.max > 3747)
565 
566 	do
567 	{
568 		return (b >= 3747) ? (3) : (b >= 1345) ? (4) : (b >= 476) ? (5) : (b >= 400) ? (6) : (b >= 347) ? (7) : (b >= 308) ? (8) : (b >= 55) ? (27) : (/* b >= 6 */ 34);
569 	}
570 
571 pragma(inline, true)
572 int BN_num_bytes(const (libressl_d.openssl.ossl_typ.BIGNUM)* a)
573 
574 	do
575 	{
576 		return (.BN_num_bits(a) + 7) / 8;
577 	}
578 
579 /* Note that BN_abs_is_word didn't work reliably for w == 0 until 0.9.8 */
580 pragma(inline, true)
581 pure nothrow @trusted @nogc @live
582 bool BN_abs_is_word(A, W)(scope const A* a, W w)
583 
584 	in
585 	{
586 		assert(a != null);
587 	}
588 
589 	do
590 	{
591 		return ((a.top == 1) && (a.d[0] == cast(.BN_ULONG)(w))) || ((w == 0) && (a.top == 0));
592 	}
593 
594 pragma(inline, true)
595 pure nothrow @trusted @nogc @live
596 bool BN_is_zero(A)(scope const A* a)
597 
598 	in
599 	{
600 		assert(a != null);
601 	}
602 
603 	do
604 	{
605 		return a.top == 0;
606 	}
607 
608 pragma(inline, true)
609 bool BN_is_one(A)(A* a)
610 
611 	in
612 	{
613 		assert(a != null);
614 	}
615 
616 	do
617 	{
618 		return (.BN_abs_is_word(a, 1)) && (!a.neg);
619 	}
620 
621 pragma(inline, true)
622 bool BN_is_word(A, W)(A* a, W w)
623 
624 	in
625 	{
626 		assert(a != null);
627 	}
628 
629 	do
630 	{
631 		return (.BN_abs_is_word(a, w)) && ((!w) || (!a.neg));
632 	}
633 
634 pragma(inline, true)
635 pure nothrow @trusted @nogc @live
636 bool BN_is_odd(A)(scope const A* a)
637 
638 	in
639 	{
640 		assert(a != null);
641 	}
642 
643 	do
644 	{
645 		return (a.top > 0) && (a.d[0] & 1);
646 	}
647 
648 pragma(inline, true)
649 int BN_one(libressl_d.openssl.ossl_typ.BIGNUM* a)
650 
651 	do
652 	{
653 		return .BN_set_word(a, 1);
654 	}
655 
656 pragma(inline, true)
657 pure nothrow @trusted @nogc @live
658 void BN_zero_ex(scope libressl_d.openssl.ossl_typ.BIGNUM* a)
659 
660 	in
661 	{
662 		assert(a != null);
663 	}
664 
665 	do
666 	{
667 		libressl_d.openssl.ossl_typ.BIGNUM* _tmp_bn = a;
668 		_tmp_bn.top = 0;
669 		_tmp_bn.neg = 0;
670 	}
671 
672 version (OPENSSL_NO_DEPRECATED) {
673 	pragma(inline, true)
674 	pure nothrow @trusted @nogc @live
675 	void BN_zero(scope libressl_d.openssl.ossl_typ.BIGNUM* a)
676 		do
677 		{
678 			.BN_zero_ex(a);
679 		}
680 } else {
681 	pragma(inline, true)
682 	int BN_zero(libressl_d.openssl.ossl_typ.BIGNUM* a)
683 
684 		do
685 		{
686 			return .BN_set_word(a, 0);
687 		}
688 }
689 
690 const (libressl_d.openssl.ossl_typ.BIGNUM)* BN_value_one();
691 char* BN_options();
692 libressl_d.openssl.ossl_typ.BN_CTX* BN_CTX_new();
693 
694 version (OPENSSL_NO_DEPRECATED) {
695 } else {
696 	void BN_CTX_init(libressl_d.openssl.ossl_typ.BN_CTX* c);
697 }
698 
699 void BN_CTX_free(libressl_d.openssl.ossl_typ.BN_CTX* c);
700 void BN_CTX_start(libressl_d.openssl.ossl_typ.BN_CTX* ctx);
701 libressl_d.openssl.ossl_typ.BIGNUM* BN_CTX_get(libressl_d.openssl.ossl_typ.BN_CTX* ctx);
702 void BN_CTX_end(libressl_d.openssl.ossl_typ.BN_CTX* ctx);
703 int BN_rand(libressl_d.openssl.ossl_typ.BIGNUM* rnd, int bits, int top, int bottom);
704 int BN_pseudo_rand(libressl_d.openssl.ossl_typ.BIGNUM* rnd, int bits, int top, int bottom);
705 int BN_rand_range(libressl_d.openssl.ossl_typ.BIGNUM* rnd, const (libressl_d.openssl.ossl_typ.BIGNUM)* range);
706 int BN_pseudo_rand_range(libressl_d.openssl.ossl_typ.BIGNUM* rnd, const (libressl_d.openssl.ossl_typ.BIGNUM)* range);
707 int BN_num_bits(const (libressl_d.openssl.ossl_typ.BIGNUM)* a);
708 int BN_num_bits_word(.BN_ULONG);
709 libressl_d.openssl.ossl_typ.BIGNUM* BN_new();
710 void BN_init(libressl_d.openssl.ossl_typ.BIGNUM*);
711 void BN_clear_free(libressl_d.openssl.ossl_typ.BIGNUM* a);
712 libressl_d.openssl.ossl_typ.BIGNUM* BN_copy(libressl_d.openssl.ossl_typ.BIGNUM* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b);
713 void BN_swap(libressl_d.openssl.ossl_typ.BIGNUM* a, libressl_d.openssl.ossl_typ.BIGNUM* b);
714 libressl_d.openssl.ossl_typ.BIGNUM* BN_bin2bn(const (ubyte)* s, int len, libressl_d.openssl.ossl_typ.BIGNUM* ret);
715 int BN_bn2bin(const (libressl_d.openssl.ossl_typ.BIGNUM)* a, ubyte* to);
716 int BN_bn2binpad(const (libressl_d.openssl.ossl_typ.BIGNUM)* a, ubyte* to, int tolen);
717 libressl_d.openssl.ossl_typ.BIGNUM* BN_lebin2bn(const (ubyte)* s, int len, libressl_d.openssl.ossl_typ.BIGNUM* ret);
718 int BN_bn2lebinpad(const (libressl_d.openssl.ossl_typ.BIGNUM)* a, ubyte* to, int tolen);
719 libressl_d.openssl.ossl_typ.BIGNUM* BN_mpi2bn(const (ubyte)* s, int len, libressl_d.openssl.ossl_typ.BIGNUM* ret);
720 int BN_bn2mpi(const (libressl_d.openssl.ossl_typ.BIGNUM)* a, ubyte* to);
721 int BN_sub(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b);
722 int BN_usub(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b);
723 int BN_uadd(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b);
724 int BN_add(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b);
725 int BN_mul(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
726 int BN_sqr(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
727 
728 /**
729  * sets sign of a BIGNUM
730  *
731  * Params:
732  *      b = pointer to the BIGNUM object
733  *      n = 0 if the BIGNUM b should be positive and a value != 0 otherwise
734  */
735 void BN_set_negative(libressl_d.openssl.ossl_typ.BIGNUM* b, int n);
736 
737 /**
738  * returns 1 if the BIGNUM is negative
739  *
740  * Params:
741  *      a = pointer to the BIGNUM object
742  *
743  * Returns: 1 if a < 0 and 0 otherwise
744  */
745 pragma(inline, true)
746 pure nothrow @trusted @nogc @live
747 bool BN_is_negative(scope const libressl_d.openssl.ossl_typ.BIGNUM* a)
748 
749 	in
750 	{
751 		assert(a != null);
752 	}
753 
754 	do
755 	{
756 		return a.neg != 0;
757 	}
758 
759 version (LIBRESSL_INTERNAL) {
760 } else {
761 	int BN_div(libressl_d.openssl.ossl_typ.BIGNUM* dv, libressl_d.openssl.ossl_typ.BIGNUM* rem, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, const (libressl_d.openssl.ossl_typ.BIGNUM)* d, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
762 
763 	pragma(inline, true)
764 	int BN_mod(libressl_d.openssl.ossl_typ.BIGNUM* rem, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, const (libressl_d.openssl.ossl_typ.BIGNUM)* d, libressl_d.openssl.ossl_typ.BN_CTX* ctx)
765 
766 		do
767 		{
768 			return .BN_div(null, rem, m, d, ctx);
769 		}
770 }
771 
772 int BN_nnmod(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, const (libressl_d.openssl.ossl_typ.BIGNUM)* d, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
773 int BN_mod_add(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
774 int BN_mod_add_quick(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, const (libressl_d.openssl.ossl_typ.BIGNUM)* m);
775 int BN_mod_sub(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
776 int BN_mod_sub_quick(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, const (libressl_d.openssl.ossl_typ.BIGNUM)* m);
777 int BN_mod_mul(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
778 int BN_mod_sqr(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
779 int BN_mod_lshift1(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
780 int BN_mod_lshift1_quick(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* m);
781 int BN_mod_lshift(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, int n, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
782 int BN_mod_lshift_quick(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, int n, const (libressl_d.openssl.ossl_typ.BIGNUM)* m);
783 
784 .BN_ULONG BN_mod_word(const (libressl_d.openssl.ossl_typ.BIGNUM)* a, .BN_ULONG w);
785 .BN_ULONG BN_div_word(libressl_d.openssl.ossl_typ.BIGNUM* a, .BN_ULONG w);
786 int BN_mul_word(libressl_d.openssl.ossl_typ.BIGNUM* a, .BN_ULONG w);
787 int BN_add_word(libressl_d.openssl.ossl_typ.BIGNUM* a, .BN_ULONG w);
788 int BN_sub_word(libressl_d.openssl.ossl_typ.BIGNUM* a, .BN_ULONG w);
789 int BN_set_word(libressl_d.openssl.ossl_typ.BIGNUM* a, .BN_ULONG w);
790 .BN_ULONG BN_get_word(const (libressl_d.openssl.ossl_typ.BIGNUM)* a);
791 
792 int BN_cmp(const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b);
793 void BN_free(libressl_d.openssl.ossl_typ.BIGNUM* a);
794 int BN_is_bit_set(const (libressl_d.openssl.ossl_typ.BIGNUM)* a, int n);
795 int BN_lshift(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, int n);
796 int BN_lshift1(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a);
797 int BN_exp(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
798 
799 version (LIBRESSL_INTERNAL) {
800 } else {
801 	int BN_mod_exp(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
802 	int BN_mod_exp_mont(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, libressl_d.openssl.ossl_typ.BN_CTX* ctx, libressl_d.openssl.ossl_typ.BN_MONT_CTX* m_ctx);
803 }
804 
805 int BN_mod_exp_mont_consttime(libressl_d.openssl.ossl_typ.BIGNUM* rr, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, libressl_d.openssl.ossl_typ.BN_CTX* ctx, libressl_d.openssl.ossl_typ.BN_MONT_CTX* in_mont);
806 int BN_mod_exp_mont_word(libressl_d.openssl.ossl_typ.BIGNUM* r, .BN_ULONG a, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, libressl_d.openssl.ossl_typ.BN_CTX* ctx, libressl_d.openssl.ossl_typ.BN_MONT_CTX* m_ctx);
807 int BN_mod_exp2_mont(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a1, const (libressl_d.openssl.ossl_typ.BIGNUM)* p1, const (libressl_d.openssl.ossl_typ.BIGNUM)* a2, const (libressl_d.openssl.ossl_typ.BIGNUM)* p2, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, libressl_d.openssl.ossl_typ.BN_CTX* ctx, libressl_d.openssl.ossl_typ.BN_MONT_CTX* m_ctx);
808 int BN_mod_exp_simple(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
809 
810 int BN_mask_bits(libressl_d.openssl.ossl_typ.BIGNUM* a, int n);
811 int BN_print_fp(libressl_d.compat.stdio.FILE* fp, const (libressl_d.openssl.ossl_typ.BIGNUM)* a);
812 int BN_print(libressl_d.openssl.bio.BIO* fp, const (libressl_d.openssl.ossl_typ.BIGNUM)* a);
813 int BN_reciprocal(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, int len, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
814 int BN_rshift(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, int n);
815 int BN_rshift1(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a);
816 void BN_clear(libressl_d.openssl.ossl_typ.BIGNUM* a);
817 libressl_d.openssl.ossl_typ.BIGNUM* BN_dup(const (libressl_d.openssl.ossl_typ.BIGNUM)* a);
818 int BN_ucmp(const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b);
819 int BN_set_bit(libressl_d.openssl.ossl_typ.BIGNUM* a, int n);
820 int BN_clear_bit(libressl_d.openssl.ossl_typ.BIGNUM* a, int n);
821 char* BN_bn2hex(const (libressl_d.openssl.ossl_typ.BIGNUM)* a);
822 char* BN_bn2dec(const (libressl_d.openssl.ossl_typ.BIGNUM)* a);
823 int BN_hex2bn(libressl_d.openssl.ossl_typ.BIGNUM** a, const (char)* str);
824 int BN_dec2bn(libressl_d.openssl.ossl_typ.BIGNUM** a, const (char)* str);
825 int BN_asc2bn(libressl_d.openssl.ossl_typ.BIGNUM** a, const (char)* str);
826 
827 version (LIBRESSL_INTERNAL) {
828 } else {
829 	int BN_gcd(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
830 }
831 
832 /**
833  * returns -2 for error
834  */
835 int BN_kronecker(const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
836 
837 version (LIBRESSL_INTERNAL) {
838 } else {
839 	libressl_d.openssl.ossl_typ.BIGNUM* BN_mod_inverse(libressl_d.openssl.ossl_typ.BIGNUM* ret, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* n, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
840 }
841 
842 libressl_d.openssl.ossl_typ.BIGNUM* BN_mod_sqrt(libressl_d.openssl.ossl_typ.BIGNUM* ret, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* n, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
843 
844 void BN_consttime_swap(.BN_ULONG swap, libressl_d.openssl.ossl_typ.BIGNUM* a, libressl_d.openssl.ossl_typ.BIGNUM* b, int nwords);
845 
846 /* Deprecated versions */
847 version (OPENSSL_NO_DEPRECATED) {
848 } else {
849 	libressl_d.openssl.ossl_typ.BIGNUM* BN_generate_prime(libressl_d.openssl.ossl_typ.BIGNUM* ret, int bits, int safe, const (libressl_d.openssl.ossl_typ.BIGNUM)* add, const (libressl_d.openssl.ossl_typ.BIGNUM)* rem, void function(int, int, void*) callback, void* cb_arg);
850 	int BN_is_prime(const (libressl_d.openssl.ossl_typ.BIGNUM)* p, int nchecks, void function(int, int, void*) callback, libressl_d.openssl.ossl_typ.BN_CTX* ctx, void* cb_arg);
851 	int BN_is_prime_fasttest(const (libressl_d.openssl.ossl_typ.BIGNUM)* p, int nchecks, void function(int, int, void*) callback, libressl_d.openssl.ossl_typ.BN_CTX* ctx, void* cb_arg, int do_trial_division);
852 }
853 
854 /* Newer versions */
855 int BN_generate_prime_ex(libressl_d.openssl.ossl_typ.BIGNUM* ret, int bits, int safe, const (libressl_d.openssl.ossl_typ.BIGNUM)* add, const (libressl_d.openssl.ossl_typ.BIGNUM)* rem, libressl_d.openssl.ossl_typ.BN_GENCB* cb);
856 int BN_is_prime_ex(const (libressl_d.openssl.ossl_typ.BIGNUM)* p, int nchecks, libressl_d.openssl.ossl_typ.BN_CTX* ctx, libressl_d.openssl.ossl_typ.BN_GENCB* cb);
857 int BN_is_prime_fasttest_ex(const (libressl_d.openssl.ossl_typ.BIGNUM)* p, int nchecks, libressl_d.openssl.ossl_typ.BN_CTX* ctx, int do_trial_division, libressl_d.openssl.ossl_typ.BN_GENCB* cb);
858 
859 int BN_X931_generate_Xpq(libressl_d.openssl.ossl_typ.BIGNUM* Xp, libressl_d.openssl.ossl_typ.BIGNUM* Xq, int nbits, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
860 
861 int BN_X931_derive_prime_ex(libressl_d.openssl.ossl_typ.BIGNUM* p, libressl_d.openssl.ossl_typ.BIGNUM* p1, libressl_d.openssl.ossl_typ.BIGNUM* p2, const (libressl_d.openssl.ossl_typ.BIGNUM)* Xp, const (libressl_d.openssl.ossl_typ.BIGNUM)* Xp1, const (libressl_d.openssl.ossl_typ.BIGNUM)* Xp2, const (libressl_d.openssl.ossl_typ.BIGNUM)* e, libressl_d.openssl.ossl_typ.BN_CTX* ctx, libressl_d.openssl.ossl_typ.BN_GENCB* cb);
862 int BN_X931_generate_prime_ex(libressl_d.openssl.ossl_typ.BIGNUM* p, libressl_d.openssl.ossl_typ.BIGNUM* p1, libressl_d.openssl.ossl_typ.BIGNUM* p2, libressl_d.openssl.ossl_typ.BIGNUM* Xp1, libressl_d.openssl.ossl_typ.BIGNUM* Xp2, const (libressl_d.openssl.ossl_typ.BIGNUM)* Xp, const (libressl_d.openssl.ossl_typ.BIGNUM)* e, libressl_d.openssl.ossl_typ.BN_CTX* ctx, libressl_d.openssl.ossl_typ.BN_GENCB* cb);
863 
864 libressl_d.openssl.ossl_typ.BN_MONT_CTX* BN_MONT_CTX_new();
865 void BN_MONT_CTX_init(libressl_d.openssl.ossl_typ.BN_MONT_CTX* ctx);
866 int BN_mod_mul_montgomery(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, libressl_d.openssl.ossl_typ.BN_MONT_CTX* mont, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
867 
868 pragma(inline, true)
869 int BN_to_montgomery(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, libressl_d.openssl.ossl_typ.BN_MONT_CTX* mont, libressl_d.openssl.ossl_typ.BN_CTX* ctx)
870 
871 	in
872 	{
873 		assert(mont != null);
874 	}
875 
876 	do
877 	{
878 		return .BN_mod_mul_montgomery(r, a, &(mont.RR), mont, ctx);
879 	}
880 
881 int BN_from_montgomery(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, libressl_d.openssl.ossl_typ.BN_MONT_CTX* mont, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
882 void BN_MONT_CTX_free(libressl_d.openssl.ossl_typ.BN_MONT_CTX* mont);
883 int BN_MONT_CTX_set(libressl_d.openssl.ossl_typ.BN_MONT_CTX* mont, const (libressl_d.openssl.ossl_typ.BIGNUM)* mod, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
884 libressl_d.openssl.ossl_typ.BN_MONT_CTX* BN_MONT_CTX_copy(libressl_d.openssl.ossl_typ.BN_MONT_CTX* to, libressl_d.openssl.ossl_typ.BN_MONT_CTX* from);
885 libressl_d.openssl.ossl_typ.BN_MONT_CTX* BN_MONT_CTX_set_locked(libressl_d.openssl.ossl_typ.BN_MONT_CTX** pmont, int lock, const (libressl_d.openssl.ossl_typ.BIGNUM)* mod, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
886 
887 /* libressl_d.openssl.ossl_typ.BN_BLINDING flags */
888 enum BN_BLINDING_NO_UPDATE = 0x00000001;
889 enum BN_BLINDING_NO_RECREATE = 0x00000002;
890 
891 libressl_d.openssl.ossl_typ.BN_BLINDING* BN_BLINDING_new(const (libressl_d.openssl.ossl_typ.BIGNUM)* A, const (libressl_d.openssl.ossl_typ.BIGNUM)* Ai, libressl_d.openssl.ossl_typ.BIGNUM* mod);
892 void BN_BLINDING_free(libressl_d.openssl.ossl_typ.BN_BLINDING* b);
893 int BN_BLINDING_update(libressl_d.openssl.ossl_typ.BN_BLINDING* b, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
894 int BN_BLINDING_convert(libressl_d.openssl.ossl_typ.BIGNUM* n, libressl_d.openssl.ossl_typ.BN_BLINDING* b, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
895 int BN_BLINDING_invert(libressl_d.openssl.ossl_typ.BIGNUM* n, libressl_d.openssl.ossl_typ.BN_BLINDING* b, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
896 int BN_BLINDING_convert_ex(libressl_d.openssl.ossl_typ.BIGNUM* n, libressl_d.openssl.ossl_typ.BIGNUM* r, libressl_d.openssl.ossl_typ.BN_BLINDING* b, libressl_d.openssl.ossl_typ.BN_CTX*);
897 int BN_BLINDING_invert_ex(libressl_d.openssl.ossl_typ.BIGNUM* n, const (libressl_d.openssl.ossl_typ.BIGNUM)* r, libressl_d.openssl.ossl_typ.BN_BLINDING* b, libressl_d.openssl.ossl_typ.BN_CTX*);
898 
899 version (OPENSSL_NO_DEPRECATED) {
900 } else {
901 	core.stdc.config.c_ulong BN_BLINDING_get_thread_id(const (libressl_d.openssl.ossl_typ.BN_BLINDING)*);
902 	void BN_BLINDING_set_thread_id(libressl_d.openssl.ossl_typ.BN_BLINDING*, core.stdc.config.c_ulong);
903 }
904 
905 libressl_d.openssl.crypto.CRYPTO_THREADID* BN_BLINDING_thread_id(libressl_d.openssl.ossl_typ.BN_BLINDING*);
906 core.stdc.config.c_ulong BN_BLINDING_get_flags(const (libressl_d.openssl.ossl_typ.BN_BLINDING)*);
907 void BN_BLINDING_set_flags(libressl_d.openssl.ossl_typ.BN_BLINDING*, core.stdc.config.c_ulong);
908 libressl_d.openssl.ossl_typ.BN_BLINDING* BN_BLINDING_create_param(libressl_d.openssl.ossl_typ.BN_BLINDING* b, const (libressl_d.openssl.ossl_typ.BIGNUM)* e, libressl_d.openssl.ossl_typ.BIGNUM* m, libressl_d.openssl.ossl_typ.BN_CTX* ctx, int function(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, libressl_d.openssl.ossl_typ.BN_CTX* ctx, libressl_d.openssl.ossl_typ.BN_MONT_CTX* m_ctx) bn_mod_exp, libressl_d.openssl.ossl_typ.BN_MONT_CTX* m_ctx);
909 
910 version (OPENSSL_NO_DEPRECATED) {
911 } else {
912 	void BN_set_params(int mul, int high, int low, int mont);
913 
914 	/**
915 	 * 0, mul, 1 high, 2 low, 3 mont
916 	 */
917 	int BN_get_params(int which);
918 }
919 
920 void BN_RECP_CTX_init(libressl_d.openssl.ossl_typ.BN_RECP_CTX* recp);
921 libressl_d.openssl.ossl_typ.BN_RECP_CTX* BN_RECP_CTX_new();
922 void BN_RECP_CTX_free(libressl_d.openssl.ossl_typ.BN_RECP_CTX* recp);
923 int BN_RECP_CTX_set(libressl_d.openssl.ossl_typ.BN_RECP_CTX* recp, const (libressl_d.openssl.ossl_typ.BIGNUM)* rdiv, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
924 int BN_mod_mul_reciprocal(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* x, const (libressl_d.openssl.ossl_typ.BIGNUM)* y, libressl_d.openssl.ossl_typ.BN_RECP_CTX* recp, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
925 int BN_mod_exp_recp(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
926 int BN_div_recp(libressl_d.openssl.ossl_typ.BIGNUM* dv, libressl_d.openssl.ossl_typ.BIGNUM* rem, const (libressl_d.openssl.ossl_typ.BIGNUM)* m, libressl_d.openssl.ossl_typ.BN_RECP_CTX* recp, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
927 
928 version (OPENSSL_NO_EC2M) {
929 } else {
930 	/*
931 	 * Functions for arithmetic over binary polynomials represented by BIGNUMs.
932 	 *
933 	 * The BIGNUM::neg property of BIGNUMs representing binary polynomials is
934 	 * ignored.
935 	 *
936 	 * Note that input arguments are not const so that their bit arrays can
937 	 * be expanded to the appropriate size if needed.
938 	 */
939 
940 	/**
941 	 * r = a + b
942 	 */
943 	int BN_GF2m_add(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b);
944 
945 	alias BN_GF2m_sub = .BN_GF2m_add;
946 
947 	/**
948 	 * r = a mod p
949 	 */
950 	int BN_GF2m_mod(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* p);
951 
952 	/**
953 	 * r = (a * b) mod p
954 	 */
955 	int BN_GF2m_mod_mul(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
956 
957 	/**
958 	 * r = (a * a) mod p
959 	 */
960 	int BN_GF2m_mod_sqr(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
961 
962 	/**
963 	 * r = (1 / b) mod p
964 	 */
965 	int BN_GF2m_mod_inv(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
966 
967 	/**
968 	 * r = (a / b) mod p
969 	 */
970 	int BN_GF2m_mod_div(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
971 
972 	/**
973 	 * r = (a ^ b) mod p
974 	 */
975 	int BN_GF2m_mod_exp(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
976 
977 	/**
978 	 * r = sqrt(a) mod p
979 	 */
980 	int BN_GF2m_mod_sqrt(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
981 
982 	/**
983 	 * r^2 + r = a mod p
984 	 */
985 	int BN_GF2m_mod_solve_quad(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
986 
987 	alias BN_GF2m_cmp = .BN_ucmp;
988 
989 	/*
990 	 * Some functions allow for representation of the irreducible polynomials
991 	 * as an uint[], say p.  The irreducible f(t) is then of the form:
992 	 *     t^p[0] + t^p[1] + ... + t^p[k]
993 	 * where m = p[0] > p[1] > ... > p[k] = 0.
994 	 */
995 	int BN_GF2m_mod_arr(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const int* p);
996 	/* r = a mod p */
997 
998 	/**
999 	 * r = (a * b) mod p
1000 	 */
1001 	int BN_GF2m_mod_mul_arr(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, const int* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
1002 
1003 	/**
1004 	 * r = (a * a) mod p
1005 	 */
1006 	int BN_GF2m_mod_sqr_arr(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const int* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
1007 
1008 	/**
1009 	 * r = (1 / b) mod p
1010 	 */
1011 	int BN_GF2m_mod_inv_arr(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, const int* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
1012 
1013 	/**
1014 	 * r = (a / b) mod p
1015 	 */
1016 	int BN_GF2m_mod_div_arr(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, const int* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
1017 
1018 	/**
1019 	 * r = (a ^ b) mod p
1020 	 */
1021 	int BN_GF2m_mod_exp_arr(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* b, const int* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
1022 
1023 	/**
1024 	 * r = sqrt(a) mod p
1025 	 */
1026 	int BN_GF2m_mod_sqrt_arr(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const int* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
1027 
1028 	/**
1029 	 * r^2 + r = a mod p
1030 	 */
1031 	int BN_GF2m_mod_solve_quad_arr(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const int* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
1032 
1033 	int BN_GF2m_poly2arr(const (libressl_d.openssl.ossl_typ.BIGNUM)* a, int* p, int max);
1034 	int BN_GF2m_arr2poly(const int* p, libressl_d.openssl.ossl_typ.BIGNUM* a);
1035 }
1036 
1037 /*
1038  * faster mod functions for the 'NIST primes'
1039  * 0 <= a < p^2
1040  */
1041 int BN_nist_mod_192(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
1042 int BN_nist_mod_224(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
1043 int BN_nist_mod_256(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
1044 int BN_nist_mod_384(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
1045 int BN_nist_mod_521(libressl_d.openssl.ossl_typ.BIGNUM* r, const (libressl_d.openssl.ossl_typ.BIGNUM)* a, const (libressl_d.openssl.ossl_typ.BIGNUM)* p, libressl_d.openssl.ossl_typ.BN_CTX* ctx);
1046 
1047 const (libressl_d.openssl.ossl_typ.BIGNUM)* BN_get0_nist_prime_192();
1048 const (libressl_d.openssl.ossl_typ.BIGNUM)* BN_get0_nist_prime_224();
1049 const (libressl_d.openssl.ossl_typ.BIGNUM)* BN_get0_nist_prime_256();
1050 const (libressl_d.openssl.ossl_typ.BIGNUM)* BN_get0_nist_prime_384();
1051 const (libressl_d.openssl.ossl_typ.BIGNUM)* BN_get0_nist_prime_521();
1052 
1053 /* Primes from RFC 2409 */
1054 libressl_d.openssl.ossl_typ.BIGNUM* get_rfc2409_prime_768(libressl_d.openssl.ossl_typ.BIGNUM* bn);
1055 libressl_d.openssl.ossl_typ.BIGNUM* get_rfc2409_prime_1024(libressl_d.openssl.ossl_typ.BIGNUM* bn);
1056 libressl_d.openssl.ossl_typ.BIGNUM* BN_get_rfc2409_prime_768(libressl_d.openssl.ossl_typ.BIGNUM* bn);
1057 libressl_d.openssl.ossl_typ.BIGNUM* BN_get_rfc2409_prime_1024(libressl_d.openssl.ossl_typ.BIGNUM* bn);
1058 
1059 /* Primes from RFC 3526 */
1060 libressl_d.openssl.ossl_typ.BIGNUM* get_rfc3526_prime_1536(libressl_d.openssl.ossl_typ.BIGNUM* bn);
1061 libressl_d.openssl.ossl_typ.BIGNUM* get_rfc3526_prime_2048(libressl_d.openssl.ossl_typ.BIGNUM* bn);
1062 libressl_d.openssl.ossl_typ.BIGNUM* get_rfc3526_prime_3072(libressl_d.openssl.ossl_typ.BIGNUM* bn);
1063 libressl_d.openssl.ossl_typ.BIGNUM* get_rfc3526_prime_4096(libressl_d.openssl.ossl_typ.BIGNUM* bn);
1064 libressl_d.openssl.ossl_typ.BIGNUM* get_rfc3526_prime_6144(libressl_d.openssl.ossl_typ.BIGNUM* bn);
1065 libressl_d.openssl.ossl_typ.BIGNUM* get_rfc3526_prime_8192(libressl_d.openssl.ossl_typ.BIGNUM* bn);
1066 libressl_d.openssl.ossl_typ.BIGNUM* BN_get_rfc3526_prime_1536(libressl_d.openssl.ossl_typ.BIGNUM* bn);
1067 libressl_d.openssl.ossl_typ.BIGNUM* BN_get_rfc3526_prime_2048(libressl_d.openssl.ossl_typ.BIGNUM* bn);
1068 libressl_d.openssl.ossl_typ.BIGNUM* BN_get_rfc3526_prime_3072(libressl_d.openssl.ossl_typ.BIGNUM* bn);
1069 libressl_d.openssl.ossl_typ.BIGNUM* BN_get_rfc3526_prime_4096(libressl_d.openssl.ossl_typ.BIGNUM* bn);
1070 libressl_d.openssl.ossl_typ.BIGNUM* BN_get_rfc3526_prime_6144(libressl_d.openssl.ossl_typ.BIGNUM* bn);
1071 libressl_d.openssl.ossl_typ.BIGNUM* BN_get_rfc3526_prime_8192(libressl_d.openssl.ossl_typ.BIGNUM* bn);
1072 
1073 /* BEGIN ERROR CODES */
1074 /**
1075  * The following lines are auto generated by the script mkerr.pl. Any changes
1076  * made after this point may be overwritten when the script is next run.
1077  */
1078 void ERR_load_BN_strings();
1079 
1080 /* Error codes for the BN functions. */
1081 
1082 /* Function codes. */
1083 enum BN_F_BNRAND = 127;
1084 enum BN_F_BN_BLINDING_CONVERT_EX = 100;
1085 enum BN_F_BN_BLINDING_CREATE_PARAM = 128;
1086 enum BN_F_BN_BLINDING_INVERT_EX = 101;
1087 enum BN_F_BN_BLINDING_NEW = 102;
1088 enum BN_F_BN_BLINDING_UPDATE = 103;
1089 enum BN_F_BN_BN2DEC = 104;
1090 enum BN_F_BN_BN2HEX = 105;
1091 enum BN_F_BN_CTX_GET = 116;
1092 enum BN_F_BN_CTX_NEW = 106;
1093 enum BN_F_BN_CTX_START = 129;
1094 enum BN_F_BN_DIV = 107;
1095 enum BN_F_BN_DIV_NO_BRANCH = 138;
1096 enum BN_F_BN_DIV_RECP = 130;
1097 enum BN_F_BN_EXP = 123;
1098 enum BN_F_BN_EXPAND2 = 108;
1099 enum BN_F_BN_GENERATE_PRIME_EX = 140;
1100 enum BN_F_BN_EXPAND_INTERNAL = 120;
1101 enum BN_F_BN_GF2M_MOD = 131;
1102 enum BN_F_BN_GF2M_MOD_EXP = 132;
1103 enum BN_F_BN_GF2M_MOD_MUL = 133;
1104 enum BN_F_BN_GF2M_MOD_SOLVE_QUAD = 134;
1105 enum BN_F_BN_GF2M_MOD_SOLVE_QUAD_ARR = 135;
1106 enum BN_F_BN_GF2M_MOD_SQR = 136;
1107 enum BN_F_BN_GF2M_MOD_SQRT = 137;
1108 enum BN_F_BN_MOD_EXP2_MONT = 118;
1109 enum BN_F_BN_MOD_EXP_MONT = 109;
1110 enum BN_F_BN_MOD_EXP_MONT_CONSTTIME = 124;
1111 enum BN_F_BN_MOD_EXP_MONT_WORD = 117;
1112 enum BN_F_BN_MOD_EXP_RECP = 125;
1113 enum BN_F_BN_MOD_EXP_SIMPLE = 126;
1114 enum BN_F_BN_MOD_INVERSE = 110;
1115 enum BN_F_BN_MOD_INVERSE_NO_BRANCH = 139;
1116 enum BN_F_BN_MOD_LSHIFT_QUICK = 119;
1117 enum BN_F_BN_MOD_MUL_RECIPROCAL = 111;
1118 enum BN_F_BN_MOD_SQRT = 121;
1119 enum BN_F_BN_MPI2BN = 112;
1120 enum BN_F_BN_NEW = 113;
1121 enum BN_F_BN_RAND = 114;
1122 enum BN_F_BN_RAND_RANGE = 122;
1123 enum BN_F_BN_USUB = 115;
1124 
1125 /* Reason codes. */
1126 enum BN_R_ARG2_LT_ARG3 = 100;
1127 enum BN_R_BAD_RECIPROCAL = 101;
1128 enum BN_R_BIGNUM_TOO_LONG = 114;
1129 enum BN_R_BITS_TOO_SMALL = 117;
1130 enum BN_R_CALLED_WITH_EVEN_MODULUS = 102;
1131 enum BN_R_DIV_BY_ZERO = 103;
1132 enum BN_R_ENCODING_ERROR = 104;
1133 enum BN_R_EXPAND_ON_STATIC_BIGNUM_DATA = 105;
1134 enum BN_R_INPUT_NOT_REDUCED = 110;
1135 enum BN_R_INVALID_LENGTH = 106;
1136 enum BN_R_INVALID_RANGE = 115;
1137 enum BN_R_NOT_A_SQUARE = 111;
1138 enum BN_R_NOT_INITIALIZED = 107;
1139 enum BN_R_NO_INVERSE = 108;
1140 enum BN_R_NO_SOLUTION = 116;
1141 enum BN_R_P_IS_NOT_PRIME = 112;
1142 enum BN_R_TOO_MANY_ITERATIONS = 113;
1143 enum BN_R_TOO_MANY_TEMPORARY_VARIABLES = 109;