bn_gf2m.c
上传用户:yisoukefu
上传日期:2020-08-09
资源大小:39506k
文件大小:29k
源码类别:

其他游戏

开发平台:

Visual C++

  1. /* crypto/bn/bn_gf2m.c */
  2. /* ====================================================================
  3.  * Copyright 2002 Sun Microsystems, Inc. ALL RIGHTS RESERVED.
  4.  *
  5.  * The Elliptic Curve Public-Key Crypto Library (ECC Code) included
  6.  * herein is developed by SUN MICROSYSTEMS, INC., and is contributed
  7.  * to the OpenSSL project.
  8.  *
  9.  * The ECC Code is licensed pursuant to the OpenSSL open source
  10.  * license provided below.
  11.  *
  12.  * In addition, Sun covenants to all licensees who provide a reciprocal
  13.  * covenant with respect to their own patents if any, not to sue under
  14.  * current and future patent claims necessarily infringed by the making,
  15.  * using, practicing, selling, offering for sale and/or otherwise
  16.  * disposing of the ECC Code as delivered hereunder (or portions thereof),
  17.  * provided that such covenant shall not apply:
  18.  *  1) for code that a licensee deletes from the ECC Code;
  19.  *  2) separates from the ECC Code; or
  20.  *  3) for infringements caused by:
  21.  *       i) the modification of the ECC Code or
  22.  *      ii) the combination of the ECC Code with other software or
  23.  *          devices where such combination causes the infringement.
  24.  *
  25.  * The software is originally written by Sheueling Chang Shantz and
  26.  * Douglas Stebila of Sun Microsystems Laboratories.
  27.  *
  28.  */
  29. /* NOTE: This file is licensed pursuant to the OpenSSL license below
  30.  * and may be modified; but after modifications, the above covenant
  31.  * may no longer apply!  In such cases, the corresponding paragraph
  32.  * ["In addition, Sun covenants ... causes the infringement."] and
  33.  * this note can be edited out; but please keep the Sun copyright
  34.  * notice and attribution. */
  35. /* ====================================================================
  36.  * Copyright (c) 1998-2002 The OpenSSL Project.  All rights reserved.
  37.  *
  38.  * Redistribution and use in source and binary forms, with or without
  39.  * modification, are permitted provided that the following conditions
  40.  * are met:
  41.  *
  42.  * 1. Redistributions of source code must retain the above copyright
  43.  *    notice, this list of conditions and the following disclaimer. 
  44.  *
  45.  * 2. Redistributions in binary form must reproduce the above copyright
  46.  *    notice, this list of conditions and the following disclaimer in
  47.  *    the documentation and/or other materials provided with the
  48.  *    distribution.
  49.  *
  50.  * 3. All advertising materials mentioning features or use of this
  51.  *    software must display the following acknowledgment:
  52.  *    "This product includes software developed by the OpenSSL Project
  53.  *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
  54.  *
  55.  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
  56.  *    endorse or promote products derived from this software without
  57.  *    prior written permission. For written permission, please contact
  58.  *    openssl-core@openssl.org.
  59.  *
  60.  * 5. Products derived from this software may not be called "OpenSSL"
  61.  *    nor may "OpenSSL" appear in their names without prior written
  62.  *    permission of the OpenSSL Project.
  63.  *
  64.  * 6. Redistributions of any form whatsoever must retain the following
  65.  *    acknowledgment:
  66.  *    "This product includes software developed by the OpenSSL Project
  67.  *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
  68.  *
  69.  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
  70.  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  71.  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
  72.  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
  73.  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
  74.  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
  75.  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
  76.  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  77.  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
  78.  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
  79.  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
  80.  * OF THE POSSIBILITY OF SUCH DAMAGE.
  81.  * ====================================================================
  82.  *
  83.  * This product includes cryptographic software written by Eric Young
  84.  * (eay@cryptsoft.com).  This product includes software written by Tim
  85.  * Hudson (tjh@cryptsoft.com).
  86.  *
  87.  */
  88. #include <assert.h>
  89. #include <limits.h>
  90. #include <stdio.h>
  91. #include "cryptlib.h"
  92. #include "bn_lcl.h"
  93. /* Maximum number of iterations before BN_GF2m_mod_solve_quad_arr should fail. */
  94. #define MAX_ITERATIONS 50
  95. static const BN_ULONG SQR_tb[16] =
  96.   {     0,     1,     4,     5,    16,    17,    20,    21,
  97.        64,    65,    68,    69,    80,    81,    84,    85 };
  98. /* Platform-specific macros to accelerate squaring. */
  99. #if defined(SIXTY_FOUR_BIT) || defined(SIXTY_FOUR_BIT_LONG)
  100. #define SQR1(w) 
  101.     SQR_tb[(w) >> 60 & 0xF] << 56 | SQR_tb[(w) >> 56 & 0xF] << 48 | 
  102.     SQR_tb[(w) >> 52 & 0xF] << 40 | SQR_tb[(w) >> 48 & 0xF] << 32 | 
  103.     SQR_tb[(w) >> 44 & 0xF] << 24 | SQR_tb[(w) >> 40 & 0xF] << 16 | 
  104.     SQR_tb[(w) >> 36 & 0xF] <<  8 | SQR_tb[(w) >> 32 & 0xF]
  105. #define SQR0(w) 
  106.     SQR_tb[(w) >> 28 & 0xF] << 56 | SQR_tb[(w) >> 24 & 0xF] << 48 | 
  107.     SQR_tb[(w) >> 20 & 0xF] << 40 | SQR_tb[(w) >> 16 & 0xF] << 32 | 
  108.     SQR_tb[(w) >> 12 & 0xF] << 24 | SQR_tb[(w) >>  8 & 0xF] << 16 | 
  109.     SQR_tb[(w) >>  4 & 0xF] <<  8 | SQR_tb[(w)       & 0xF]
  110. #endif
  111. #ifdef THIRTY_TWO_BIT
  112. #define SQR1(w) 
  113.     SQR_tb[(w) >> 28 & 0xF] << 24 | SQR_tb[(w) >> 24 & 0xF] << 16 | 
  114.     SQR_tb[(w) >> 20 & 0xF] <<  8 | SQR_tb[(w) >> 16 & 0xF]
  115. #define SQR0(w) 
  116.     SQR_tb[(w) >> 12 & 0xF] << 24 | SQR_tb[(w) >>  8 & 0xF] << 16 | 
  117.     SQR_tb[(w) >>  4 & 0xF] <<  8 | SQR_tb[(w)       & 0xF]
  118. #endif
  119. #ifdef SIXTEEN_BIT
  120. #define SQR1(w) 
  121.     SQR_tb[(w) >> 12 & 0xF] <<  8 | SQR_tb[(w) >>  8 & 0xF]
  122. #define SQR0(w) 
  123.     SQR_tb[(w) >>  4 & 0xF] <<  8 | SQR_tb[(w)       & 0xF]
  124. #endif
  125. #ifdef EIGHT_BIT
  126. #define SQR1(w) 
  127.     SQR_tb[(w) >>  4 & 0xF]
  128. #define SQR0(w) 
  129.     SQR_tb[(w)       & 15]
  130. #endif
  131. /* Product of two polynomials a, b each with degree < BN_BITS2 - 1,
  132.  * result is a polynomial r with degree < 2 * BN_BITS - 1
  133.  * The caller MUST ensure that the variables have the right amount
  134.  * of space allocated.
  135.  */
  136. #ifdef EIGHT_BIT
  137. static void bn_GF2m_mul_1x1(BN_ULONG *r1, BN_ULONG *r0, const BN_ULONG a, const BN_ULONG b)
  138. {
  139. register BN_ULONG h, l, s;
  140. BN_ULONG tab[4], top1b = a >> 7;
  141. register BN_ULONG a1, a2;
  142. a1 = a & (0x7F); a2 = a1 << 1;
  143. tab[0] = 0; tab[1] = a1; tab[2] = a2; tab[3] = a1^a2;
  144. s = tab[b      & 0x3]; l  = s;
  145. s = tab[b >> 2 & 0x3]; l ^= s << 2; h  = s >> 6;
  146. s = tab[b >> 4 & 0x3]; l ^= s << 4; h ^= s >> 4;
  147. s = tab[b >> 6      ]; l ^= s << 6; h ^= s >> 2;
  148. /* compensate for the top bit of a */
  149. if (top1b & 01) { l ^= b << 7; h ^= b >> 1; } 
  150. *r1 = h; *r0 = l;
  151. #endif
  152. #ifdef SIXTEEN_BIT
  153. static void bn_GF2m_mul_1x1(BN_ULONG *r1, BN_ULONG *r0, const BN_ULONG a, const BN_ULONG b)
  154. {
  155. register BN_ULONG h, l, s;
  156. BN_ULONG tab[4], top1b = a >> 15; 
  157. register BN_ULONG a1, a2;
  158. a1 = a & (0x7FFF); a2 = a1 << 1;
  159. tab[0] = 0; tab[1] = a1; tab[2] = a2; tab[3] = a1^a2;
  160. s = tab[b      & 0x3]; l  = s;
  161. s = tab[b >> 2 & 0x3]; l ^= s <<  2; h  = s >> 14;
  162. s = tab[b >> 4 & 0x3]; l ^= s <<  4; h ^= s >> 12;
  163. s = tab[b >> 6 & 0x3]; l ^= s <<  6; h ^= s >> 10;
  164. s = tab[b >> 8 & 0x3]; l ^= s <<  8; h ^= s >>  8;
  165. s = tab[b >>10 & 0x3]; l ^= s << 10; h ^= s >>  6;
  166. s = tab[b >>12 & 0x3]; l ^= s << 12; h ^= s >>  4;
  167. s = tab[b >>14      ]; l ^= s << 14; h ^= s >>  2;
  168. /* compensate for the top bit of a */
  169. if (top1b & 01) { l ^= b << 15; h ^= b >> 1; } 
  170. *r1 = h; *r0 = l;
  171. #endif
  172. #ifdef THIRTY_TWO_BIT
  173. static void bn_GF2m_mul_1x1(BN_ULONG *r1, BN_ULONG *r0, const BN_ULONG a, const BN_ULONG b)
  174. {
  175. register BN_ULONG h, l, s;
  176. BN_ULONG tab[8], top2b = a >> 30; 
  177. register BN_ULONG a1, a2, a4;
  178. a1 = a & (0x3FFFFFFF); a2 = a1 << 1; a4 = a2 << 1;
  179. tab[0] =  0; tab[1] = a1;    tab[2] = a2;    tab[3] = a1^a2;
  180. tab[4] = a4; tab[5] = a1^a4; tab[6] = a2^a4; tab[7] = a1^a2^a4;
  181. s = tab[b       & 0x7]; l  = s;
  182. s = tab[b >>  3 & 0x7]; l ^= s <<  3; h  = s >> 29;
  183. s = tab[b >>  6 & 0x7]; l ^= s <<  6; h ^= s >> 26;
  184. s = tab[b >>  9 & 0x7]; l ^= s <<  9; h ^= s >> 23;
  185. s = tab[b >> 12 & 0x7]; l ^= s << 12; h ^= s >> 20;
  186. s = tab[b >> 15 & 0x7]; l ^= s << 15; h ^= s >> 17;
  187. s = tab[b >> 18 & 0x7]; l ^= s << 18; h ^= s >> 14;
  188. s = tab[b >> 21 & 0x7]; l ^= s << 21; h ^= s >> 11;
  189. s = tab[b >> 24 & 0x7]; l ^= s << 24; h ^= s >>  8;
  190. s = tab[b >> 27 & 0x7]; l ^= s << 27; h ^= s >>  5;
  191. s = tab[b >> 30      ]; l ^= s << 30; h ^= s >>  2;
  192. /* compensate for the top two bits of a */
  193. if (top2b & 01) { l ^= b << 30; h ^= b >> 2; } 
  194. if (top2b & 02) { l ^= b << 31; h ^= b >> 1; } 
  195. *r1 = h; *r0 = l;
  196. #endif
  197. #if defined(SIXTY_FOUR_BIT) || defined(SIXTY_FOUR_BIT_LONG)
  198. static void bn_GF2m_mul_1x1(BN_ULONG *r1, BN_ULONG *r0, const BN_ULONG a, const BN_ULONG b)
  199. {
  200. register BN_ULONG h, l, s;
  201. BN_ULONG tab[16], top3b = a >> 61;
  202. register BN_ULONG a1, a2, a4, a8;
  203. a1 = a & (0x1FFFFFFFFFFFFFFFULL); a2 = a1 << 1; a4 = a2 << 1; a8 = a4 << 1;
  204. tab[ 0] = 0;     tab[ 1] = a1;       tab[ 2] = a2;       tab[ 3] = a1^a2;
  205. tab[ 4] = a4;    tab[ 5] = a1^a4;    tab[ 6] = a2^a4;    tab[ 7] = a1^a2^a4;
  206. tab[ 8] = a8;    tab[ 9] = a1^a8;    tab[10] = a2^a8;    tab[11] = a1^a2^a8;
  207. tab[12] = a4^a8; tab[13] = a1^a4^a8; tab[14] = a2^a4^a8; tab[15] = a1^a2^a4^a8;
  208. s = tab[b       & 0xF]; l  = s;
  209. s = tab[b >>  4 & 0xF]; l ^= s <<  4; h  = s >> 60;
  210. s = tab[b >>  8 & 0xF]; l ^= s <<  8; h ^= s >> 56;
  211. s = tab[b >> 12 & 0xF]; l ^= s << 12; h ^= s >> 52;
  212. s = tab[b >> 16 & 0xF]; l ^= s << 16; h ^= s >> 48;
  213. s = tab[b >> 20 & 0xF]; l ^= s << 20; h ^= s >> 44;
  214. s = tab[b >> 24 & 0xF]; l ^= s << 24; h ^= s >> 40;
  215. s = tab[b >> 28 & 0xF]; l ^= s << 28; h ^= s >> 36;
  216. s = tab[b >> 32 & 0xF]; l ^= s << 32; h ^= s >> 32;
  217. s = tab[b >> 36 & 0xF]; l ^= s << 36; h ^= s >> 28;
  218. s = tab[b >> 40 & 0xF]; l ^= s << 40; h ^= s >> 24;
  219. s = tab[b >> 44 & 0xF]; l ^= s << 44; h ^= s >> 20;
  220. s = tab[b >> 48 & 0xF]; l ^= s << 48; h ^= s >> 16;
  221. s = tab[b >> 52 & 0xF]; l ^= s << 52; h ^= s >> 12;
  222. s = tab[b >> 56 & 0xF]; l ^= s << 56; h ^= s >>  8;
  223. s = tab[b >> 60      ]; l ^= s << 60; h ^= s >>  4;
  224. /* compensate for the top three bits of a */
  225. if (top3b & 01) { l ^= b << 61; h ^= b >> 3; } 
  226. if (top3b & 02) { l ^= b << 62; h ^= b >> 2; } 
  227. if (top3b & 04) { l ^= b << 63; h ^= b >> 1; } 
  228. *r1 = h; *r0 = l;
  229. #endif
  230. /* Product of two polynomials a, b each with degree < 2 * BN_BITS2 - 1,
  231.  * result is a polynomial r with degree < 4 * BN_BITS2 - 1
  232.  * The caller MUST ensure that the variables have the right amount
  233.  * of space allocated.
  234.  */
  235. static void bn_GF2m_mul_2x2(BN_ULONG *r, const BN_ULONG a1, const BN_ULONG a0, const BN_ULONG b1, const BN_ULONG b0)
  236. {
  237. BN_ULONG m1, m0;
  238. /* r[3] = h1, r[2] = h0; r[1] = l1; r[0] = l0 */
  239. bn_GF2m_mul_1x1(r+3, r+2, a1, b1);
  240. bn_GF2m_mul_1x1(r+1, r, a0, b0);
  241. bn_GF2m_mul_1x1(&m1, &m0, a0 ^ a1, b0 ^ b1);
  242. /* Correction on m1 ^= l1 ^ h1; m0 ^= l0 ^ h0; */
  243. r[2] ^= m1 ^ r[1] ^ r[3];  /* h0 ^= m1 ^ l1 ^ h1; */
  244. r[1] = r[3] ^ r[2] ^ r[0] ^ m1 ^ m0;  /* l1 ^= l0 ^ h0 ^ m0; */
  245. }
  246. /* Add polynomials a and b and store result in r; r could be a or b, a and b 
  247.  * could be equal; r is the bitwise XOR of a and b.
  248.  */
  249. int BN_GF2m_add(BIGNUM *r, const BIGNUM *a, const BIGNUM *b)
  250. {
  251. int i;
  252. const BIGNUM *at, *bt;
  253. bn_check_top(a);
  254. bn_check_top(b);
  255. if (a->top < b->top) { at = b; bt = a; }
  256. else { at = a; bt = b; }
  257. bn_wexpand(r, at->top);
  258. for (i = 0; i < bt->top; i++)
  259. {
  260. r->d[i] = at->d[i] ^ bt->d[i];
  261. }
  262. for (; i < at->top; i++)
  263. {
  264. r->d[i] = at->d[i];
  265. }
  266. r->top = at->top;
  267. bn_correct_top(r);
  268. return 1;
  269. }
  270. /* Some functions allow for representation of the irreducible polynomials
  271.  * as an int[], say p.  The irreducible f(t) is then of the form:
  272.  *     t^p[0] + t^p[1] + ... + t^p[k]
  273.  * where m = p[0] > p[1] > ... > p[k] = 0.
  274.  */
  275. /* Performs modular reduction of a and store result in r.  r could be a. */
  276. int BN_GF2m_mod_arr(BIGNUM *r, const BIGNUM *a, const unsigned int p[])
  277. {
  278. int j, k;
  279. int n, dN, d0, d1;
  280. BN_ULONG zz, *z;
  281. bn_check_top(a);
  282. if (!p[0])
  283. {
  284. /* reduction mod 1 => return 0 */
  285. BN_zero(r);
  286. return 1;
  287. }
  288. /* Since the algorithm does reduction in the r value, if a != r, copy
  289.  * the contents of a into r so we can do reduction in r. 
  290.  */
  291. if (a != r)
  292. {
  293. if (!bn_wexpand(r, a->top)) return 0;
  294. for (j = 0; j < a->top; j++)
  295. {
  296. r->d[j] = a->d[j];
  297. }
  298. r->top = a->top;
  299. }
  300. z = r->d;
  301. /* start reduction */
  302. dN = p[0] / BN_BITS2;  
  303. for (j = r->top - 1; j > dN;)
  304. {
  305. zz = z[j];
  306. if (z[j] == 0) { j--; continue; }
  307. z[j] = 0;
  308. for (k = 1; p[k] != 0; k++)
  309. {
  310. /* reducing component t^p[k] */
  311. n = p[0] - p[k];
  312. d0 = n % BN_BITS2;  d1 = BN_BITS2 - d0;
  313. n /= BN_BITS2; 
  314. z[j-n] ^= (zz>>d0);
  315. if (d0) z[j-n-1] ^= (zz<<d1);
  316. }
  317. /* reducing component t^0 */
  318. n = dN;  
  319. d0 = p[0] % BN_BITS2;
  320. d1 = BN_BITS2 - d0;
  321. z[j-n] ^= (zz >> d0);
  322. if (d0) z[j-n-1] ^= (zz << d1);
  323. }
  324. /* final round of reduction */
  325. while (j == dN)
  326. {
  327. d0 = p[0] % BN_BITS2;
  328. zz = z[dN] >> d0;
  329. if (zz == 0) break;
  330. d1 = BN_BITS2 - d0;
  331. if (d0) z[dN] = (z[dN] << d1) >> d1; /* clear up the top d1 bits */
  332. z[0] ^= zz; /* reduction t^0 component */
  333. for (k = 1; p[k] != 0; k++)
  334. {
  335. BN_ULONG tmp_ulong;
  336. /* reducing component t^p[k]*/
  337. n = p[k] / BN_BITS2;   
  338. d0 = p[k] % BN_BITS2;
  339. d1 = BN_BITS2 - d0;
  340. z[n] ^= (zz << d0);
  341. tmp_ulong = zz >> d1;
  342.                         if (d0 && tmp_ulong)
  343.                                 z[n+1] ^= tmp_ulong;
  344. }
  345. }
  346. bn_correct_top(r);
  347. return 1;
  348. }
  349. /* Performs modular reduction of a by p and store result in r.  r could be a.
  350.  *
  351.  * This function calls down to the BN_GF2m_mod_arr implementation; this wrapper
  352.  * function is only provided for convenience; for best performance, use the 
  353.  * BN_GF2m_mod_arr function.
  354.  */
  355. int BN_GF2m_mod(BIGNUM *r, const BIGNUM *a, const BIGNUM *p)
  356. {
  357. int ret = 0;
  358. const int max = BN_num_bits(p);
  359. unsigned int *arr=NULL;
  360. bn_check_top(a);
  361. bn_check_top(p);
  362. if ((arr = (unsigned int *)OPENSSL_malloc(sizeof(unsigned int) * max)) == NULL) goto err;
  363. ret = BN_GF2m_poly2arr(p, arr, max);
  364. if (!ret || ret > max)
  365. {
  366. BNerr(BN_F_BN_GF2M_MOD,BN_R_INVALID_LENGTH);
  367. goto err;
  368. }
  369. ret = BN_GF2m_mod_arr(r, a, arr);
  370. bn_check_top(r);
  371. err:
  372. if (arr) OPENSSL_free(arr);
  373. return ret;
  374. }
  375. /* Compute the product of two polynomials a and b, reduce modulo p, and store
  376.  * the result in r.  r could be a or b; a could be b.
  377.  */
  378. int BN_GF2m_mod_mul_arr(BIGNUM *r, const BIGNUM *a, const BIGNUM *b, const unsigned int p[], BN_CTX *ctx)
  379. {
  380. int zlen, i, j, k, ret = 0;
  381. BIGNUM *s;
  382. BN_ULONG x1, x0, y1, y0, zz[4];
  383. bn_check_top(a);
  384. bn_check_top(b);
  385. if (a == b)
  386. {
  387. return BN_GF2m_mod_sqr_arr(r, a, p, ctx);
  388. }
  389. BN_CTX_start(ctx);
  390. if ((s = BN_CTX_get(ctx)) == NULL) goto err;
  391. zlen = a->top + b->top + 4;
  392. if (!bn_wexpand(s, zlen)) goto err;
  393. s->top = zlen;
  394. for (i = 0; i < zlen; i++) s->d[i] = 0;
  395. for (j = 0; j < b->top; j += 2)
  396. {
  397. y0 = b->d[j];
  398. y1 = ((j+1) == b->top) ? 0 : b->d[j+1];
  399. for (i = 0; i < a->top; i += 2)
  400. {
  401. x0 = a->d[i];
  402. x1 = ((i+1) == a->top) ? 0 : a->d[i+1];
  403. bn_GF2m_mul_2x2(zz, x1, x0, y1, y0);
  404. for (k = 0; k < 4; k++) s->d[i+j+k] ^= zz[k];
  405. }
  406. }
  407. bn_correct_top(s);
  408. if (BN_GF2m_mod_arr(r, s, p))
  409. ret = 1;
  410. bn_check_top(r);
  411. err:
  412. BN_CTX_end(ctx);
  413. return ret;
  414. }
  415. /* Compute the product of two polynomials a and b, reduce modulo p, and store
  416.  * the result in r.  r could be a or b; a could equal b.
  417.  *
  418.  * This function calls down to the BN_GF2m_mod_mul_arr implementation; this wrapper
  419.  * function is only provided for convenience; for best performance, use the 
  420.  * BN_GF2m_mod_mul_arr function.
  421.  */
  422. int BN_GF2m_mod_mul(BIGNUM *r, const BIGNUM *a, const BIGNUM *b, const BIGNUM *p, BN_CTX *ctx)
  423. {
  424. int ret = 0;
  425. const int max = BN_num_bits(p);
  426. unsigned int *arr=NULL;
  427. bn_check_top(a);
  428. bn_check_top(b);
  429. bn_check_top(p);
  430. if ((arr = (unsigned int *)OPENSSL_malloc(sizeof(unsigned int) * max)) == NULL) goto err;
  431. ret = BN_GF2m_poly2arr(p, arr, max);
  432. if (!ret || ret > max)
  433. {
  434. BNerr(BN_F_BN_GF2M_MOD_MUL,BN_R_INVALID_LENGTH);
  435. goto err;
  436. }
  437. ret = BN_GF2m_mod_mul_arr(r, a, b, arr, ctx);
  438. bn_check_top(r);
  439. err:
  440. if (arr) OPENSSL_free(arr);
  441. return ret;
  442. }
  443. /* Square a, reduce the result mod p, and store it in a.  r could be a. */
  444. int BN_GF2m_mod_sqr_arr(BIGNUM *r, const BIGNUM *a, const unsigned int p[], BN_CTX *ctx)
  445. {
  446. int i, ret = 0;
  447. BIGNUM *s;
  448. bn_check_top(a);
  449. BN_CTX_start(ctx);
  450. if ((s = BN_CTX_get(ctx)) == NULL) return 0;
  451. if (!bn_wexpand(s, 2 * a->top)) goto err;
  452. for (i = a->top - 1; i >= 0; i--)
  453. {
  454. s->d[2*i+1] = SQR1(a->d[i]);
  455. s->d[2*i  ] = SQR0(a->d[i]);
  456. }
  457. s->top = 2 * a->top;
  458. bn_correct_top(s);
  459. if (!BN_GF2m_mod_arr(r, s, p)) goto err;
  460. bn_check_top(r);
  461. ret = 1;
  462. err:
  463. BN_CTX_end(ctx);
  464. return ret;
  465. }
  466. /* Square a, reduce the result mod p, and store it in a.  r could be a.
  467.  *
  468.  * This function calls down to the BN_GF2m_mod_sqr_arr implementation; this wrapper
  469.  * function is only provided for convenience; for best performance, use the 
  470.  * BN_GF2m_mod_sqr_arr function.
  471.  */
  472. int BN_GF2m_mod_sqr(BIGNUM *r, const BIGNUM *a, const BIGNUM *p, BN_CTX *ctx)
  473. {
  474. int ret = 0;
  475. const int max = BN_num_bits(p);
  476. unsigned int *arr=NULL;
  477. bn_check_top(a);
  478. bn_check_top(p);
  479. if ((arr = (unsigned int *)OPENSSL_malloc(sizeof(unsigned int) * max)) == NULL) goto err;
  480. ret = BN_GF2m_poly2arr(p, arr, max);
  481. if (!ret || ret > max)
  482. {
  483. BNerr(BN_F_BN_GF2M_MOD_SQR,BN_R_INVALID_LENGTH);
  484. goto err;
  485. }
  486. ret = BN_GF2m_mod_sqr_arr(r, a, arr, ctx);
  487. bn_check_top(r);
  488. err:
  489. if (arr) OPENSSL_free(arr);
  490. return ret;
  491. }
  492. /* Invert a, reduce modulo p, and store the result in r. r could be a. 
  493.  * Uses Modified Almost Inverse Algorithm (Algorithm 10) from
  494.  *     Hankerson, D., Hernandez, J.L., and Menezes, A.  "Software Implementation
  495.  *     of Elliptic Curve Cryptography Over Binary Fields".
  496.  */
  497. int BN_GF2m_mod_inv(BIGNUM *r, const BIGNUM *a, const BIGNUM *p, BN_CTX *ctx)
  498. {
  499. BIGNUM *b, *c, *u, *v, *tmp;
  500. int ret = 0;
  501. bn_check_top(a);
  502. bn_check_top(p);
  503. BN_CTX_start(ctx);
  504. b = BN_CTX_get(ctx);
  505. c = BN_CTX_get(ctx);
  506. u = BN_CTX_get(ctx);
  507. v = BN_CTX_get(ctx);
  508. if (v == NULL) goto err;
  509. if (!BN_one(b)) goto err;
  510. if (!BN_GF2m_mod(u, a, p)) goto err;
  511. if (!BN_copy(v, p)) goto err;
  512. if (BN_is_zero(u)) goto err;
  513. while (1)
  514. {
  515. while (!BN_is_odd(u))
  516. {
  517. if (!BN_rshift1(u, u)) goto err;
  518. if (BN_is_odd(b))
  519. {
  520. if (!BN_GF2m_add(b, b, p)) goto err;
  521. }
  522. if (!BN_rshift1(b, b)) goto err;
  523. }
  524. if (BN_abs_is_word(u, 1)) break;
  525. if (BN_num_bits(u) < BN_num_bits(v))
  526. {
  527. tmp = u; u = v; v = tmp;
  528. tmp = b; b = c; c = tmp;
  529. }
  530. if (!BN_GF2m_add(u, u, v)) goto err;
  531. if (!BN_GF2m_add(b, b, c)) goto err;
  532. }
  533. if (!BN_copy(r, b)) goto err;
  534. bn_check_top(r);
  535. ret = 1;
  536. err:
  537.    BN_CTX_end(ctx);
  538. return ret;
  539. }
  540. /* Invert xx, reduce modulo p, and store the result in r. r could be xx. 
  541.  *
  542.  * This function calls down to the BN_GF2m_mod_inv implementation; this wrapper
  543.  * function is only provided for convenience; for best performance, use the 
  544.  * BN_GF2m_mod_inv function.
  545.  */
  546. int BN_GF2m_mod_inv_arr(BIGNUM *r, const BIGNUM *xx, const unsigned int p[], BN_CTX *ctx)
  547. {
  548. BIGNUM *field;
  549. int ret = 0;
  550. bn_check_top(xx);
  551. BN_CTX_start(ctx);
  552. if ((field = BN_CTX_get(ctx)) == NULL) goto err;
  553. if (!BN_GF2m_arr2poly(p, field)) goto err;
  554. ret = BN_GF2m_mod_inv(r, xx, field, ctx);
  555. bn_check_top(r);
  556. err:
  557. BN_CTX_end(ctx);
  558. return ret;
  559. }
  560. #ifndef OPENSSL_SUN_GF2M_DIV
  561. /* Divide y by x, reduce modulo p, and store the result in r. r could be x 
  562.  * or y, x could equal y.
  563.  */
  564. int BN_GF2m_mod_div(BIGNUM *r, const BIGNUM *y, const BIGNUM *x, const BIGNUM *p, BN_CTX *ctx)
  565. {
  566. BIGNUM *xinv = NULL;
  567. int ret = 0;
  568. bn_check_top(y);
  569. bn_check_top(x);
  570. bn_check_top(p);
  571. BN_CTX_start(ctx);
  572. xinv = BN_CTX_get(ctx);
  573. if (xinv == NULL) goto err;
  574. if (!BN_GF2m_mod_inv(xinv, x, p, ctx)) goto err;
  575. if (!BN_GF2m_mod_mul(r, y, xinv, p, ctx)) goto err;
  576. bn_check_top(r);
  577. ret = 1;
  578. err:
  579. BN_CTX_end(ctx);
  580. return ret;
  581. }
  582. #else
  583. /* Divide y by x, reduce modulo p, and store the result in r. r could be x 
  584.  * or y, x could equal y.
  585.  * Uses algorithm Modular_Division_GF(2^m) from 
  586.  *     Chang-Shantz, S.  "From Euclid's GCD to Montgomery Multiplication to 
  587.  *     the Great Divide".
  588.  */
  589. int BN_GF2m_mod_div(BIGNUM *r, const BIGNUM *y, const BIGNUM *x, const BIGNUM *p, BN_CTX *ctx)
  590. {
  591. BIGNUM *a, *b, *u, *v;
  592. int ret = 0;
  593. bn_check_top(y);
  594. bn_check_top(x);
  595. bn_check_top(p);
  596. BN_CTX_start(ctx);
  597. a = BN_CTX_get(ctx);
  598. b = BN_CTX_get(ctx);
  599. u = BN_CTX_get(ctx);
  600. v = BN_CTX_get(ctx);
  601. if (v == NULL) goto err;
  602. /* reduce x and y mod p */
  603. if (!BN_GF2m_mod(u, y, p)) goto err;
  604. if (!BN_GF2m_mod(a, x, p)) goto err;
  605. if (!BN_copy(b, p)) goto err;
  606. while (!BN_is_odd(a))
  607. {
  608. if (!BN_rshift1(a, a)) goto err;
  609. if (BN_is_odd(u)) if (!BN_GF2m_add(u, u, p)) goto err;
  610. if (!BN_rshift1(u, u)) goto err;
  611. }
  612. do
  613. {
  614. if (BN_GF2m_cmp(b, a) > 0)
  615. {
  616. if (!BN_GF2m_add(b, b, a)) goto err;
  617. if (!BN_GF2m_add(v, v, u)) goto err;
  618. do
  619. {
  620. if (!BN_rshift1(b, b)) goto err;
  621. if (BN_is_odd(v)) if (!BN_GF2m_add(v, v, p)) goto err;
  622. if (!BN_rshift1(v, v)) goto err;
  623. } while (!BN_is_odd(b));
  624. }
  625. else if (BN_abs_is_word(a, 1))
  626. break;
  627. else
  628. {
  629. if (!BN_GF2m_add(a, a, b)) goto err;
  630. if (!BN_GF2m_add(u, u, v)) goto err;
  631. do
  632. {
  633. if (!BN_rshift1(a, a)) goto err;
  634. if (BN_is_odd(u)) if (!BN_GF2m_add(u, u, p)) goto err;
  635. if (!BN_rshift1(u, u)) goto err;
  636. } while (!BN_is_odd(a));
  637. }
  638. } while (1);
  639. if (!BN_copy(r, u)) goto err;
  640. bn_check_top(r);
  641. ret = 1;
  642. err:
  643.    BN_CTX_end(ctx);
  644. return ret;
  645. }
  646. #endif
  647. /* Divide yy by xx, reduce modulo p, and store the result in r. r could be xx 
  648.  * or yy, xx could equal yy.
  649.  *
  650.  * This function calls down to the BN_GF2m_mod_div implementation; this wrapper
  651.  * function is only provided for convenience; for best performance, use the 
  652.  * BN_GF2m_mod_div function.
  653.  */
  654. int BN_GF2m_mod_div_arr(BIGNUM *r, const BIGNUM *yy, const BIGNUM *xx, const unsigned int p[], BN_CTX *ctx)
  655. {
  656. BIGNUM *field;
  657. int ret = 0;
  658. bn_check_top(yy);
  659. bn_check_top(xx);
  660. BN_CTX_start(ctx);
  661. if ((field = BN_CTX_get(ctx)) == NULL) goto err;
  662. if (!BN_GF2m_arr2poly(p, field)) goto err;
  663. ret = BN_GF2m_mod_div(r, yy, xx, field, ctx);
  664. bn_check_top(r);
  665. err:
  666. BN_CTX_end(ctx);
  667. return ret;
  668. }
  669. /* Compute the bth power of a, reduce modulo p, and store
  670.  * the result in r.  r could be a.
  671.  * Uses simple square-and-multiply algorithm A.5.1 from IEEE P1363.
  672.  */
  673. int BN_GF2m_mod_exp_arr(BIGNUM *r, const BIGNUM *a, const BIGNUM *b, const unsigned int p[], BN_CTX *ctx)
  674. {
  675. int ret = 0, i, n;
  676. BIGNUM *u;
  677. bn_check_top(a);
  678. bn_check_top(b);
  679. if (BN_is_zero(b))
  680. return(BN_one(r));
  681. if (BN_abs_is_word(b, 1))
  682. return (BN_copy(r, a) != NULL);
  683. BN_CTX_start(ctx);
  684. if ((u = BN_CTX_get(ctx)) == NULL) goto err;
  685. if (!BN_GF2m_mod_arr(u, a, p)) goto err;
  686. n = BN_num_bits(b) - 1;
  687. for (i = n - 1; i >= 0; i--)
  688. {
  689. if (!BN_GF2m_mod_sqr_arr(u, u, p, ctx)) goto err;
  690. if (BN_is_bit_set(b, i))
  691. {
  692. if (!BN_GF2m_mod_mul_arr(u, u, a, p, ctx)) goto err;
  693. }
  694. }
  695. if (!BN_copy(r, u)) goto err;
  696. bn_check_top(r);
  697. ret = 1;
  698. err:
  699. BN_CTX_end(ctx);
  700. return ret;
  701. }
  702. /* Compute the bth power of a, reduce modulo p, and store
  703.  * the result in r.  r could be a.
  704.  *
  705.  * This function calls down to the BN_GF2m_mod_exp_arr implementation; this wrapper
  706.  * function is only provided for convenience; for best performance, use the 
  707.  * BN_GF2m_mod_exp_arr function.
  708.  */
  709. int BN_GF2m_mod_exp(BIGNUM *r, const BIGNUM *a, const BIGNUM *b, const BIGNUM *p, BN_CTX *ctx)
  710. {
  711. int ret = 0;
  712. const int max = BN_num_bits(p);
  713. unsigned int *arr=NULL;
  714. bn_check_top(a);
  715. bn_check_top(b);
  716. bn_check_top(p);
  717. if ((arr = (unsigned int *)OPENSSL_malloc(sizeof(unsigned int) * max)) == NULL) goto err;
  718. ret = BN_GF2m_poly2arr(p, arr, max);
  719. if (!ret || ret > max)
  720. {
  721. BNerr(BN_F_BN_GF2M_MOD_EXP,BN_R_INVALID_LENGTH);
  722. goto err;
  723. }
  724. ret = BN_GF2m_mod_exp_arr(r, a, b, arr, ctx);
  725. bn_check_top(r);
  726. err:
  727. if (arr) OPENSSL_free(arr);
  728. return ret;
  729. }
  730. /* Compute the square root of a, reduce modulo p, and store
  731.  * the result in r.  r could be a.
  732.  * Uses exponentiation as in algorithm A.4.1 from IEEE P1363.
  733.  */
  734. int BN_GF2m_mod_sqrt_arr(BIGNUM *r, const BIGNUM *a, const unsigned int p[], BN_CTX *ctx)
  735. {
  736. int ret = 0;
  737. BIGNUM *u;
  738. bn_check_top(a);
  739. if (!p[0])
  740. {
  741. /* reduction mod 1 => return 0 */
  742. BN_zero(r);
  743. return 1;
  744. }
  745. BN_CTX_start(ctx);
  746. if ((u = BN_CTX_get(ctx)) == NULL) goto err;
  747. if (!BN_set_bit(u, p[0] - 1)) goto err;
  748. ret = BN_GF2m_mod_exp_arr(r, a, u, p, ctx);
  749. bn_check_top(r);
  750. err:
  751. BN_CTX_end(ctx);
  752. return ret;
  753. }
  754. /* Compute the square root of a, reduce modulo p, and store
  755.  * the result in r.  r could be a.
  756.  *
  757.  * This function calls down to the BN_GF2m_mod_sqrt_arr implementation; this wrapper
  758.  * function is only provided for convenience; for best performance, use the 
  759.  * BN_GF2m_mod_sqrt_arr function.
  760.  */
  761. int BN_GF2m_mod_sqrt(BIGNUM *r, const BIGNUM *a, const BIGNUM *p, BN_CTX *ctx)
  762. {
  763. int ret = 0;
  764. const int max = BN_num_bits(p);
  765. unsigned int *arr=NULL;
  766. bn_check_top(a);
  767. bn_check_top(p);
  768. if ((arr = (unsigned int *)OPENSSL_malloc(sizeof(unsigned int) * max)) == NULL) goto err;
  769. ret = BN_GF2m_poly2arr(p, arr, max);
  770. if (!ret || ret > max)
  771. {
  772. BNerr(BN_F_BN_GF2M_MOD_SQRT,BN_R_INVALID_LENGTH);
  773. goto err;
  774. }
  775. ret = BN_GF2m_mod_sqrt_arr(r, a, arr, ctx);
  776. bn_check_top(r);
  777. err:
  778. if (arr) OPENSSL_free(arr);
  779. return ret;
  780. }
  781. /* Find r such that r^2 + r = a mod p.  r could be a. If no r exists returns 0.
  782.  * Uses algorithms A.4.7 and A.4.6 from IEEE P1363.
  783.  */
  784. int BN_GF2m_mod_solve_quad_arr(BIGNUM *r, const BIGNUM *a_, const unsigned int p[], BN_CTX *ctx)
  785. {
  786. int ret = 0, count = 0;
  787. unsigned int j;
  788. BIGNUM *a, *z, *rho, *w, *w2, *tmp;
  789. bn_check_top(a_);
  790. if (!p[0])
  791. {
  792. /* reduction mod 1 => return 0 */
  793. BN_zero(r);
  794. return 1;
  795. }
  796. BN_CTX_start(ctx);
  797. a = BN_CTX_get(ctx);
  798. z = BN_CTX_get(ctx);
  799. w = BN_CTX_get(ctx);
  800. if (w == NULL) goto err;
  801. if (!BN_GF2m_mod_arr(a, a_, p)) goto err;
  802. if (BN_is_zero(a))
  803. {
  804. BN_zero(r);
  805. ret = 1;
  806. goto err;
  807. }
  808. if (p[0] & 0x1) /* m is odd */
  809. {
  810. /* compute half-trace of a */
  811. if (!BN_copy(z, a)) goto err;
  812. for (j = 1; j <= (p[0] - 1) / 2; j++)
  813. {
  814. if (!BN_GF2m_mod_sqr_arr(z, z, p, ctx)) goto err;
  815. if (!BN_GF2m_mod_sqr_arr(z, z, p, ctx)) goto err;
  816. if (!BN_GF2m_add(z, z, a)) goto err;
  817. }
  818. }
  819. else /* m is even */
  820. {
  821. rho = BN_CTX_get(ctx);
  822. w2 = BN_CTX_get(ctx);
  823. tmp = BN_CTX_get(ctx);
  824. if (tmp == NULL) goto err;
  825. do
  826. {
  827. if (!BN_rand(rho, p[0], 0, 0)) goto err;
  828. if (!BN_GF2m_mod_arr(rho, rho, p)) goto err;
  829. BN_zero(z);
  830. if (!BN_copy(w, rho)) goto err;
  831. for (j = 1; j <= p[0] - 1; j++)
  832. {
  833. if (!BN_GF2m_mod_sqr_arr(z, z, p, ctx)) goto err;
  834. if (!BN_GF2m_mod_sqr_arr(w2, w, p, ctx)) goto err;
  835. if (!BN_GF2m_mod_mul_arr(tmp, w2, a, p, ctx)) goto err;
  836. if (!BN_GF2m_add(z, z, tmp)) goto err;
  837. if (!BN_GF2m_add(w, w2, rho)) goto err;
  838. }
  839. count++;
  840. } while (BN_is_zero(w) && (count < MAX_ITERATIONS));
  841. if (BN_is_zero(w))
  842. {
  843. BNerr(BN_F_BN_GF2M_MOD_SOLVE_QUAD_ARR,BN_R_TOO_MANY_ITERATIONS);
  844. goto err;
  845. }
  846. }
  847. if (!BN_GF2m_mod_sqr_arr(w, z, p, ctx)) goto err;
  848. if (!BN_GF2m_add(w, z, w)) goto err;
  849. if (BN_GF2m_cmp(w, a))
  850. {
  851. BNerr(BN_F_BN_GF2M_MOD_SOLVE_QUAD_ARR, BN_R_NO_SOLUTION);
  852. goto err;
  853. }
  854. if (!BN_copy(r, z)) goto err;
  855. bn_check_top(r);
  856. ret = 1;
  857. err:
  858. BN_CTX_end(ctx);
  859. return ret;
  860. }
  861. /* Find r such that r^2 + r = a mod p.  r could be a. If no r exists returns 0.
  862.  *
  863.  * This function calls down to the BN_GF2m_mod_solve_quad_arr implementation; this wrapper
  864.  * function is only provided for convenience; for best performance, use the 
  865.  * BN_GF2m_mod_solve_quad_arr function.
  866.  */
  867. int BN_GF2m_mod_solve_quad(BIGNUM *r, const BIGNUM *a, const BIGNUM *p, BN_CTX *ctx)
  868. {
  869. int ret = 0;
  870. const int max = BN_num_bits(p);
  871. unsigned int *arr=NULL;
  872. bn_check_top(a);
  873. bn_check_top(p);
  874. if ((arr = (unsigned int *)OPENSSL_malloc(sizeof(unsigned int) *
  875. max)) == NULL) goto err;
  876. ret = BN_GF2m_poly2arr(p, arr, max);
  877. if (!ret || ret > max)
  878. {
  879. BNerr(BN_F_BN_GF2M_MOD_SOLVE_QUAD,BN_R_INVALID_LENGTH);
  880. goto err;
  881. }
  882. ret = BN_GF2m_mod_solve_quad_arr(r, a, arr, ctx);
  883. bn_check_top(r);
  884. err:
  885. if (arr) OPENSSL_free(arr);
  886. return ret;
  887. }
  888. /* Convert the bit-string representation of a polynomial
  889.  * ( sum_{i=0}^n a_i * x^i , where a_0 is *not* zero) into an array
  890.  * of integers corresponding to the bits with non-zero coefficient.
  891.  * Up to max elements of the array will be filled.  Return value is total
  892.  * number of coefficients that would be extracted if array was large enough.
  893.  */
  894. int BN_GF2m_poly2arr(const BIGNUM *a, unsigned int p[], int max)
  895. {
  896. int i, j, k = 0;
  897. BN_ULONG mask;
  898. if (BN_is_zero(a) || !BN_is_bit_set(a, 0))
  899. /* a_0 == 0 => return error (the unsigned int array
  900.  * must be terminated by 0)
  901.  */
  902. return 0;
  903. for (i = a->top - 1; i >= 0; i--)
  904. {
  905. if (!a->d[i])
  906. /* skip word if a->d[i] == 0 */
  907. continue;
  908. mask = BN_TBIT;
  909. for (j = BN_BITS2 - 1; j >= 0; j--)
  910. {
  911. if (a->d[i] & mask) 
  912. {
  913. if (k < max) p[k] = BN_BITS2 * i + j;
  914. k++;
  915. }
  916. mask >>= 1;
  917. }
  918. }
  919. return k;
  920. }
  921. /* Convert the coefficient array representation of a polynomial to a 
  922.  * bit-string.  The array must be terminated by 0.
  923.  */
  924. int BN_GF2m_arr2poly(const unsigned int p[], BIGNUM *a)
  925. {
  926. int i;
  927. bn_check_top(a);
  928. BN_zero(a);
  929. for (i = 0; p[i] != 0; i++)
  930. {
  931. if (BN_set_bit(a, p[i]) == 0)
  932. return 0;
  933. }
  934. BN_set_bit(a, 0);
  935. bn_check_top(a);
  936. return 1;
  937. }