os/ossrv/ssl/libcrypto/src/crypto/bn/bn_asm.c
author sl
Tue, 10 Jun 2014 14:32:02 +0200
changeset 1 260cb5ec6c19
permissions -rw-r--r--
Update contrib.
sl@0
     1
/* crypto/bn/bn_asm.c */
sl@0
     2
/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
sl@0
     3
 * All rights reserved.
sl@0
     4
 *
sl@0
     5
 * This package is an SSL implementation written
sl@0
     6
 * by Eric Young (eay@cryptsoft.com).
sl@0
     7
 * The implementation was written so as to conform with Netscapes SSL.
sl@0
     8
 * 
sl@0
     9
 * This library is free for commercial and non-commercial use as long as
sl@0
    10
 * the following conditions are aheared to.  The following conditions
sl@0
    11
 * apply to all code found in this distribution, be it the RC4, RSA,
sl@0
    12
 * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
sl@0
    13
 * included with this distribution is covered by the same copyright terms
sl@0
    14
 * except that the holder is Tim Hudson (tjh@cryptsoft.com).
sl@0
    15
 * 
sl@0
    16
 * Copyright remains Eric Young's, and as such any Copyright notices in
sl@0
    17
 * the code are not to be removed.
sl@0
    18
 * If this package is used in a product, Eric Young should be given attribution
sl@0
    19
 * as the author of the parts of the library used.
sl@0
    20
 * This can be in the form of a textual message at program startup or
sl@0
    21
 * in documentation (online or textual) provided with the package.
sl@0
    22
 * 
sl@0
    23
 * Redistribution and use in source and binary forms, with or without
sl@0
    24
 * modification, are permitted provided that the following conditions
sl@0
    25
 * are met:
sl@0
    26
 * 1. Redistributions of source code must retain the copyright
sl@0
    27
 *    notice, this list of conditions and the following disclaimer.
sl@0
    28
 * 2. Redistributions in binary form must reproduce the above copyright
sl@0
    29
 *    notice, this list of conditions and the following disclaimer in the
sl@0
    30
 *    documentation and/or other materials provided with the distribution.
sl@0
    31
 * 3. All advertising materials mentioning features or use of this software
sl@0
    32
 *    must display the following acknowledgement:
sl@0
    33
 *    "This product includes cryptographic software written by
sl@0
    34
 *     Eric Young (eay@cryptsoft.com)"
sl@0
    35
 *    The word 'cryptographic' can be left out if the rouines from the library
sl@0
    36
 *    being used are not cryptographic related :-).
sl@0
    37
 * 4. If you include any Windows specific code (or a derivative thereof) from 
sl@0
    38
 *    the apps directory (application code) you must include an acknowledgement:
sl@0
    39
 *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
sl@0
    40
 * 
sl@0
    41
 * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
sl@0
    42
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
sl@0
    43
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
sl@0
    44
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
sl@0
    45
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
sl@0
    46
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
sl@0
    47
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
sl@0
    48
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
sl@0
    49
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
sl@0
    50
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
sl@0
    51
 * SUCH DAMAGE.
sl@0
    52
 * 
sl@0
    53
 * The licence and distribution terms for any publically available version or
sl@0
    54
 * derivative of this code cannot be changed.  i.e. this code cannot simply be
sl@0
    55
 * copied and put under another distribution licence
sl@0
    56
 * [including the GNU Public Licence.]
sl@0
    57
 */
sl@0
    58
sl@0
    59
#ifndef BN_DEBUG
sl@0
    60
# undef NDEBUG /* avoid conflicting definitions */
sl@0
    61
# define NDEBUG
sl@0
    62
#endif
sl@0
    63
sl@0
    64
#include <stdio.h>
sl@0
    65
#include <assert.h>
sl@0
    66
#include "cryptlib.h"
sl@0
    67
#include "bn_lcl.h"
sl@0
    68
sl@0
    69
#if defined(BN_LLONG) || defined(BN_UMULT_HIGH)
sl@0
    70
sl@0
    71
EXPORT_C BN_ULONG bn_mul_add_words(BN_ULONG *rp, const BN_ULONG *ap, int num, BN_ULONG w)
sl@0
    72
	{
sl@0
    73
	BN_ULONG c1=0;
sl@0
    74
sl@0
    75
	assert(num >= 0);
sl@0
    76
	if (num <= 0) return(c1);
sl@0
    77
sl@0
    78
	while (num&~3)
sl@0
    79
		{
sl@0
    80
		mul_add(rp[0],ap[0],w,c1);
sl@0
    81
		mul_add(rp[1],ap[1],w,c1);
sl@0
    82
		mul_add(rp[2],ap[2],w,c1);
sl@0
    83
		mul_add(rp[3],ap[3],w,c1);
sl@0
    84
		ap+=4; rp+=4; num-=4;
sl@0
    85
		}
sl@0
    86
	if (num)
sl@0
    87
		{
sl@0
    88
		mul_add(rp[0],ap[0],w,c1); if (--num==0) return c1;
sl@0
    89
		mul_add(rp[1],ap[1],w,c1); if (--num==0) return c1;
sl@0
    90
		mul_add(rp[2],ap[2],w,c1); return c1;
sl@0
    91
		}
sl@0
    92
	
sl@0
    93
	return(c1);
sl@0
    94
	} 
sl@0
    95
sl@0
    96
EXPORT_C BN_ULONG bn_mul_words(BN_ULONG *rp, const BN_ULONG *ap, int num, BN_ULONG w)
sl@0
    97
	{
sl@0
    98
	BN_ULONG c1=0;
sl@0
    99
sl@0
   100
	assert(num >= 0);
sl@0
   101
	if (num <= 0) return(c1);
sl@0
   102
sl@0
   103
	while (num&~3)
sl@0
   104
		{
sl@0
   105
		mul(rp[0],ap[0],w,c1);
sl@0
   106
		mul(rp[1],ap[1],w,c1);
sl@0
   107
		mul(rp[2],ap[2],w,c1);
sl@0
   108
		mul(rp[3],ap[3],w,c1);
sl@0
   109
		ap+=4; rp+=4; num-=4;
sl@0
   110
		}
sl@0
   111
	if (num)
sl@0
   112
		{
sl@0
   113
		mul(rp[0],ap[0],w,c1); if (--num == 0) return c1;
sl@0
   114
		mul(rp[1],ap[1],w,c1); if (--num == 0) return c1;
sl@0
   115
		mul(rp[2],ap[2],w,c1);
sl@0
   116
		}
sl@0
   117
	return(c1);
sl@0
   118
	} 
sl@0
   119
sl@0
   120
EXPORT_C void bn_sqr_words(BN_ULONG *r, const BN_ULONG *a, int n)
sl@0
   121
        {
sl@0
   122
	assert(n >= 0);
sl@0
   123
	if (n <= 0) return;
sl@0
   124
	while (n&~3)
sl@0
   125
		{
sl@0
   126
		sqr(r[0],r[1],a[0]);
sl@0
   127
		sqr(r[2],r[3],a[1]);
sl@0
   128
		sqr(r[4],r[5],a[2]);
sl@0
   129
		sqr(r[6],r[7],a[3]);
sl@0
   130
		a+=4; r+=8; n-=4;
sl@0
   131
		}
sl@0
   132
	if (n)
sl@0
   133
		{
sl@0
   134
		sqr(r[0],r[1],a[0]); if (--n == 0) return;
sl@0
   135
		sqr(r[2],r[3],a[1]); if (--n == 0) return;
sl@0
   136
		sqr(r[4],r[5],a[2]);
sl@0
   137
		}
sl@0
   138
	}
sl@0
   139
sl@0
   140
#else /* !(defined(BN_LLONG) || defined(BN_UMULT_HIGH)) */
sl@0
   141
sl@0
   142
EXPORT_C BN_ULONG bn_mul_add_words(BN_ULONG *rp, const BN_ULONG *ap, int num, BN_ULONG w)
sl@0
   143
	{
sl@0
   144
	BN_ULONG c=0;
sl@0
   145
	BN_ULONG bl,bh;
sl@0
   146
sl@0
   147
	assert(num >= 0);
sl@0
   148
	if (num <= 0) return((BN_ULONG)0);
sl@0
   149
sl@0
   150
	bl=LBITS(w);
sl@0
   151
	bh=HBITS(w);
sl@0
   152
sl@0
   153
	for (;;)
sl@0
   154
		{
sl@0
   155
		mul_add(rp[0],ap[0],bl,bh,c);
sl@0
   156
		if (--num == 0) break;
sl@0
   157
		mul_add(rp[1],ap[1],bl,bh,c);
sl@0
   158
		if (--num == 0) break;
sl@0
   159
		mul_add(rp[2],ap[2],bl,bh,c);
sl@0
   160
		if (--num == 0) break;
sl@0
   161
		mul_add(rp[3],ap[3],bl,bh,c);
sl@0
   162
		if (--num == 0) break;
sl@0
   163
		ap+=4;
sl@0
   164
		rp+=4;
sl@0
   165
		}
sl@0
   166
	return(c);
sl@0
   167
	} 
sl@0
   168
sl@0
   169
EXPORT_C BN_ULONG bn_mul_words(BN_ULONG *rp, const BN_ULONG *ap, int num, BN_ULONG w)
sl@0
   170
	{
sl@0
   171
	BN_ULONG carry=0;
sl@0
   172
	BN_ULONG bl,bh;
sl@0
   173
sl@0
   174
	assert(num >= 0);
sl@0
   175
	if (num <= 0) return((BN_ULONG)0);
sl@0
   176
sl@0
   177
	bl=LBITS(w);
sl@0
   178
	bh=HBITS(w);
sl@0
   179
sl@0
   180
	for (;;)
sl@0
   181
		{
sl@0
   182
		mul(rp[0],ap[0],bl,bh,carry);
sl@0
   183
		if (--num == 0) break;
sl@0
   184
		mul(rp[1],ap[1],bl,bh,carry);
sl@0
   185
		if (--num == 0) break;
sl@0
   186
		mul(rp[2],ap[2],bl,bh,carry);
sl@0
   187
		if (--num == 0) break;
sl@0
   188
		mul(rp[3],ap[3],bl,bh,carry);
sl@0
   189
		if (--num == 0) break;
sl@0
   190
		ap+=4;
sl@0
   191
		rp+=4;
sl@0
   192
		}
sl@0
   193
	return(carry);
sl@0
   194
	} 
sl@0
   195
sl@0
   196
EXPORT_C void bn_sqr_words(BN_ULONG *r, const BN_ULONG *a, int n)
sl@0
   197
        {
sl@0
   198
	assert(n >= 0);
sl@0
   199
	if (n <= 0) return;
sl@0
   200
	for (;;)
sl@0
   201
		{
sl@0
   202
		sqr64(r[0],r[1],a[0]);
sl@0
   203
		if (--n == 0) break;
sl@0
   204
sl@0
   205
		sqr64(r[2],r[3],a[1]);
sl@0
   206
		if (--n == 0) break;
sl@0
   207
sl@0
   208
		sqr64(r[4],r[5],a[2]);
sl@0
   209
		if (--n == 0) break;
sl@0
   210
sl@0
   211
		sqr64(r[6],r[7],a[3]);
sl@0
   212
		if (--n == 0) break;
sl@0
   213
sl@0
   214
		a+=4;
sl@0
   215
		r+=8;
sl@0
   216
		}
sl@0
   217
	}
sl@0
   218
sl@0
   219
#endif /* !(defined(BN_LLONG) || defined(BN_UMULT_HIGH)) */
sl@0
   220
sl@0
   221
#if defined(BN_LLONG) && defined(BN_DIV2W)
sl@0
   222
sl@0
   223
EXPORT_C BN_ULONG bn_div_words(BN_ULONG h, BN_ULONG l, BN_ULONG d)
sl@0
   224
	{
sl@0
   225
	return((BN_ULONG)(((((BN_ULLONG)h)<<BN_BITS2)|l)/(BN_ULLONG)d));
sl@0
   226
	}
sl@0
   227
sl@0
   228
#else
sl@0
   229
sl@0
   230
/* Divide h,l by d and return the result. */
sl@0
   231
/* I need to test this some more :-( */
sl@0
   232
EXPORT_C BN_ULONG bn_div_words(BN_ULONG h, BN_ULONG l, BN_ULONG d)
sl@0
   233
	{
sl@0
   234
	BN_ULONG dh,dl,q,ret=0,th,tl,t;
sl@0
   235
	int i,count=2;
sl@0
   236
sl@0
   237
	if (d == 0) return(BN_MASK2);
sl@0
   238
sl@0
   239
	i=BN_num_bits_word(d);
sl@0
   240
	assert((i == BN_BITS2) || (h <= (BN_ULONG)1<<i));
sl@0
   241
sl@0
   242
	i=BN_BITS2-i;
sl@0
   243
	if (h >= d) h-=d;
sl@0
   244
sl@0
   245
	if (i)
sl@0
   246
		{
sl@0
   247
		d<<=i;
sl@0
   248
		h=(h<<i)|(l>>(BN_BITS2-i));
sl@0
   249
		l<<=i;
sl@0
   250
		}
sl@0
   251
	dh=(d&BN_MASK2h)>>BN_BITS4;
sl@0
   252
	dl=(d&BN_MASK2l);
sl@0
   253
	for (;;)
sl@0
   254
		{
sl@0
   255
		if ((h>>BN_BITS4) == dh)
sl@0
   256
			q=BN_MASK2l;
sl@0
   257
		else
sl@0
   258
			q=h/dh;
sl@0
   259
sl@0
   260
		th=q*dh;
sl@0
   261
		tl=dl*q;
sl@0
   262
		for (;;)
sl@0
   263
			{
sl@0
   264
			t=h-th;
sl@0
   265
			if ((t&BN_MASK2h) ||
sl@0
   266
				((tl) <= (
sl@0
   267
					(t<<BN_BITS4)|
sl@0
   268
					((l&BN_MASK2h)>>BN_BITS4))))
sl@0
   269
				break;
sl@0
   270
			q--;
sl@0
   271
			th-=dh;
sl@0
   272
			tl-=dl;
sl@0
   273
			}
sl@0
   274
		t=(tl>>BN_BITS4);
sl@0
   275
		tl=(tl<<BN_BITS4)&BN_MASK2h;
sl@0
   276
		th+=t;
sl@0
   277
sl@0
   278
		if (l < tl) th++;
sl@0
   279
		l-=tl;
sl@0
   280
		if (h < th)
sl@0
   281
			{
sl@0
   282
			h+=d;
sl@0
   283
			q--;
sl@0
   284
			}
sl@0
   285
		h-=th;
sl@0
   286
sl@0
   287
		if (--count == 0) break;
sl@0
   288
sl@0
   289
		ret=q<<BN_BITS4;
sl@0
   290
		h=((h<<BN_BITS4)|(l>>BN_BITS4))&BN_MASK2;
sl@0
   291
		l=(l&BN_MASK2l)<<BN_BITS4;
sl@0
   292
		}
sl@0
   293
	ret|=q;
sl@0
   294
	return(ret);
sl@0
   295
	}
sl@0
   296
#endif /* !defined(BN_LLONG) && defined(BN_DIV2W) */
sl@0
   297
sl@0
   298
#ifdef BN_LLONG
sl@0
   299
EXPORT_C BN_ULONG bn_add_words(BN_ULONG *r, const BN_ULONG *a, const BN_ULONG *b, int n)
sl@0
   300
        {
sl@0
   301
	BN_ULLONG ll=0;
sl@0
   302
sl@0
   303
	assert(n >= 0);
sl@0
   304
	if (n <= 0) return((BN_ULONG)0);
sl@0
   305
sl@0
   306
	for (;;)
sl@0
   307
		{
sl@0
   308
		ll+=(BN_ULLONG)a[0]+b[0];
sl@0
   309
		r[0]=(BN_ULONG)ll&BN_MASK2;
sl@0
   310
		ll>>=BN_BITS2;
sl@0
   311
		if (--n <= 0) break;
sl@0
   312
sl@0
   313
		ll+=(BN_ULLONG)a[1]+b[1];
sl@0
   314
		r[1]=(BN_ULONG)ll&BN_MASK2;
sl@0
   315
		ll>>=BN_BITS2;
sl@0
   316
		if (--n <= 0) break;
sl@0
   317
sl@0
   318
		ll+=(BN_ULLONG)a[2]+b[2];
sl@0
   319
		r[2]=(BN_ULONG)ll&BN_MASK2;
sl@0
   320
		ll>>=BN_BITS2;
sl@0
   321
		if (--n <= 0) break;
sl@0
   322
sl@0
   323
		ll+=(BN_ULLONG)a[3]+b[3];
sl@0
   324
		r[3]=(BN_ULONG)ll&BN_MASK2;
sl@0
   325
		ll>>=BN_BITS2;
sl@0
   326
		if (--n <= 0) break;
sl@0
   327
sl@0
   328
		a+=4;
sl@0
   329
		b+=4;
sl@0
   330
		r+=4;
sl@0
   331
		}
sl@0
   332
	return((BN_ULONG)ll);
sl@0
   333
	}
sl@0
   334
#else /* !BN_LLONG */
sl@0
   335
EXPORT_C BN_ULONG bn_add_words(BN_ULONG *r, const BN_ULONG *a, const BN_ULONG *b, int n)
sl@0
   336
        {
sl@0
   337
	BN_ULONG c,l,t;
sl@0
   338
sl@0
   339
	assert(n >= 0);
sl@0
   340
	if (n <= 0) return((BN_ULONG)0);
sl@0
   341
sl@0
   342
	c=0;
sl@0
   343
	for (;;)
sl@0
   344
		{
sl@0
   345
		t=a[0];
sl@0
   346
		t=(t+c)&BN_MASK2;
sl@0
   347
		c=(t < c);
sl@0
   348
		l=(t+b[0])&BN_MASK2;
sl@0
   349
		c+=(l < t);
sl@0
   350
		r[0]=l;
sl@0
   351
		if (--n <= 0) break;
sl@0
   352
sl@0
   353
		t=a[1];
sl@0
   354
		t=(t+c)&BN_MASK2;
sl@0
   355
		c=(t < c);
sl@0
   356
		l=(t+b[1])&BN_MASK2;
sl@0
   357
		c+=(l < t);
sl@0
   358
		r[1]=l;
sl@0
   359
		if (--n <= 0) break;
sl@0
   360
sl@0
   361
		t=a[2];
sl@0
   362
		t=(t+c)&BN_MASK2;
sl@0
   363
		c=(t < c);
sl@0
   364
		l=(t+b[2])&BN_MASK2;
sl@0
   365
		c+=(l < t);
sl@0
   366
		r[2]=l;
sl@0
   367
		if (--n <= 0) break;
sl@0
   368
sl@0
   369
		t=a[3];
sl@0
   370
		t=(t+c)&BN_MASK2;
sl@0
   371
		c=(t < c);
sl@0
   372
		l=(t+b[3])&BN_MASK2;
sl@0
   373
		c+=(l < t);
sl@0
   374
		r[3]=l;
sl@0
   375
		if (--n <= 0) break;
sl@0
   376
sl@0
   377
		a+=4;
sl@0
   378
		b+=4;
sl@0
   379
		r+=4;
sl@0
   380
		}
sl@0
   381
	return((BN_ULONG)c);
sl@0
   382
	}
sl@0
   383
#endif /* !BN_LLONG */
sl@0
   384
sl@0
   385
EXPORT_C BN_ULONG bn_sub_words(BN_ULONG *r, const BN_ULONG *a, const BN_ULONG *b, int n)
sl@0
   386
        {
sl@0
   387
	BN_ULONG t1,t2;
sl@0
   388
	int c=0;
sl@0
   389
sl@0
   390
	assert(n >= 0);
sl@0
   391
	if (n <= 0) return((BN_ULONG)0);
sl@0
   392
sl@0
   393
	for (;;)
sl@0
   394
		{
sl@0
   395
		t1=a[0]; t2=b[0];
sl@0
   396
		r[0]=(t1-t2-c)&BN_MASK2;
sl@0
   397
		if (t1 != t2) c=(t1 < t2);
sl@0
   398
		if (--n <= 0) break;
sl@0
   399
sl@0
   400
		t1=a[1]; t2=b[1];
sl@0
   401
		r[1]=(t1-t2-c)&BN_MASK2;
sl@0
   402
		if (t1 != t2) c=(t1 < t2);
sl@0
   403
		if (--n <= 0) break;
sl@0
   404
sl@0
   405
		t1=a[2]; t2=b[2];
sl@0
   406
		r[2]=(t1-t2-c)&BN_MASK2;
sl@0
   407
		if (t1 != t2) c=(t1 < t2);
sl@0
   408
		if (--n <= 0) break;
sl@0
   409
sl@0
   410
		t1=a[3]; t2=b[3];
sl@0
   411
		r[3]=(t1-t2-c)&BN_MASK2;
sl@0
   412
		if (t1 != t2) c=(t1 < t2);
sl@0
   413
		if (--n <= 0) break;
sl@0
   414
sl@0
   415
		a+=4;
sl@0
   416
		b+=4;
sl@0
   417
		r+=4;
sl@0
   418
		}
sl@0
   419
	return(c);
sl@0
   420
	}
sl@0
   421
sl@0
   422
#ifdef BN_MUL_COMBA
sl@0
   423
sl@0
   424
#undef bn_mul_comba8
sl@0
   425
#undef bn_mul_comba4
sl@0
   426
#undef bn_sqr_comba8
sl@0
   427
#undef bn_sqr_comba4
sl@0
   428
sl@0
   429
/* mul_add_c(a,b,c0,c1,c2)  -- c+=a*b for three word number c=(c2,c1,c0) */
sl@0
   430
/* mul_add_c2(a,b,c0,c1,c2) -- c+=2*a*b for three word number c=(c2,c1,c0) */
sl@0
   431
/* sqr_add_c(a,i,c0,c1,c2)  -- c+=a[i]^2 for three word number c=(c2,c1,c0) */
sl@0
   432
/* sqr_add_c2(a,i,c0,c1,c2) -- c+=2*a[i]*a[j] for three word number c=(c2,c1,c0) */
sl@0
   433
sl@0
   434
#ifdef BN_LLONG
sl@0
   435
#define mul_add_c(a,b,c0,c1,c2) \
sl@0
   436
	t=(BN_ULLONG)a*b; \
sl@0
   437
	t1=(BN_ULONG)Lw(t); \
sl@0
   438
	t2=(BN_ULONG)Hw(t); \
sl@0
   439
	c0=(c0+t1)&BN_MASK2; if ((c0) < t1) t2++; \
sl@0
   440
	c1=(c1+t2)&BN_MASK2; if ((c1) < t2) c2++;
sl@0
   441
sl@0
   442
#define mul_add_c2(a,b,c0,c1,c2) \
sl@0
   443
	t=(BN_ULLONG)a*b; \
sl@0
   444
	tt=(t+t)&BN_MASK; \
sl@0
   445
	if (tt < t) c2++; \
sl@0
   446
	t1=(BN_ULONG)Lw(tt); \
sl@0
   447
	t2=(BN_ULONG)Hw(tt); \
sl@0
   448
	c0=(c0+t1)&BN_MASK2;  \
sl@0
   449
	if ((c0 < t1) && (((++t2)&BN_MASK2) == 0)) c2++; \
sl@0
   450
	c1=(c1+t2)&BN_MASK2; if ((c1) < t2) c2++;
sl@0
   451
sl@0
   452
#define sqr_add_c(a,i,c0,c1,c2) \
sl@0
   453
	t=(BN_ULLONG)a[i]*a[i]; \
sl@0
   454
	t1=(BN_ULONG)Lw(t); \
sl@0
   455
	t2=(BN_ULONG)Hw(t); \
sl@0
   456
	c0=(c0+t1)&BN_MASK2; if ((c0) < t1) t2++; \
sl@0
   457
	c1=(c1+t2)&BN_MASK2; if ((c1) < t2) c2++;
sl@0
   458
sl@0
   459
#define sqr_add_c2(a,i,j,c0,c1,c2) \
sl@0
   460
	mul_add_c2((a)[i],(a)[j],c0,c1,c2)
sl@0
   461
sl@0
   462
#elif defined(BN_UMULT_LOHI)
sl@0
   463
sl@0
   464
#define mul_add_c(a,b,c0,c1,c2)	{	\
sl@0
   465
	BN_ULONG ta=(a),tb=(b);		\
sl@0
   466
	BN_UMULT_LOHI(t1,t2,ta,tb);	\
sl@0
   467
	c0 += t1; t2 += (c0<t1)?1:0;	\
sl@0
   468
	c1 += t2; c2 += (c1<t2)?1:0;	\
sl@0
   469
	}
sl@0
   470
sl@0
   471
#define mul_add_c2(a,b,c0,c1,c2) {	\
sl@0
   472
	BN_ULONG ta=(a),tb=(b),t0;	\
sl@0
   473
	BN_UMULT_LOHI(t0,t1,ta,tb);	\
sl@0
   474
	t2 = t1+t1; c2 += (t2<t1)?1:0;	\
sl@0
   475
	t1 = t0+t0; t2 += (t1<t0)?1:0;	\
sl@0
   476
	c0 += t1; t2 += (c0<t1)?1:0;	\
sl@0
   477
	c1 += t2; c2 += (c1<t2)?1:0;	\
sl@0
   478
	}
sl@0
   479
sl@0
   480
#define sqr_add_c(a,i,c0,c1,c2)	{	\
sl@0
   481
	BN_ULONG ta=(a)[i];		\
sl@0
   482
	BN_UMULT_LOHI(t1,t2,ta,ta);	\
sl@0
   483
	c0 += t1; t2 += (c0<t1)?1:0;	\
sl@0
   484
	c1 += t2; c2 += (c1<t2)?1:0;	\
sl@0
   485
	}
sl@0
   486
sl@0
   487
#define sqr_add_c2(a,i,j,c0,c1,c2)	\
sl@0
   488
	mul_add_c2((a)[i],(a)[j],c0,c1,c2)
sl@0
   489
sl@0
   490
#elif defined(BN_UMULT_HIGH)
sl@0
   491
sl@0
   492
#define mul_add_c(a,b,c0,c1,c2)	{	\
sl@0
   493
	BN_ULONG ta=(a),tb=(b);		\
sl@0
   494
	t1 = ta * tb;			\
sl@0
   495
	t2 = BN_UMULT_HIGH(ta,tb);	\
sl@0
   496
	c0 += t1; t2 += (c0<t1)?1:0;	\
sl@0
   497
	c1 += t2; c2 += (c1<t2)?1:0;	\
sl@0
   498
	}
sl@0
   499
sl@0
   500
#define mul_add_c2(a,b,c0,c1,c2) {	\
sl@0
   501
	BN_ULONG ta=(a),tb=(b),t0;	\
sl@0
   502
	t1 = BN_UMULT_HIGH(ta,tb);	\
sl@0
   503
	t0 = ta * tb;			\
sl@0
   504
	t2 = t1+t1; c2 += (t2<t1)?1:0;	\
sl@0
   505
	t1 = t0+t0; t2 += (t1<t0)?1:0;	\
sl@0
   506
	c0 += t1; t2 += (c0<t1)?1:0;	\
sl@0
   507
	c1 += t2; c2 += (c1<t2)?1:0;	\
sl@0
   508
	}
sl@0
   509
sl@0
   510
#define sqr_add_c(a,i,c0,c1,c2)	{	\
sl@0
   511
	BN_ULONG ta=(a)[i];		\
sl@0
   512
	t1 = ta * ta;			\
sl@0
   513
	t2 = BN_UMULT_HIGH(ta,ta);	\
sl@0
   514
	c0 += t1; t2 += (c0<t1)?1:0;	\
sl@0
   515
	c1 += t2; c2 += (c1<t2)?1:0;	\
sl@0
   516
	}
sl@0
   517
sl@0
   518
#define sqr_add_c2(a,i,j,c0,c1,c2)	\
sl@0
   519
	mul_add_c2((a)[i],(a)[j],c0,c1,c2)
sl@0
   520
sl@0
   521
#else /* !BN_LLONG */
sl@0
   522
#define mul_add_c(a,b,c0,c1,c2) \
sl@0
   523
	t1=LBITS(a); t2=HBITS(a); \
sl@0
   524
	bl=LBITS(b); bh=HBITS(b); \
sl@0
   525
	mul64(t1,t2,bl,bh); \
sl@0
   526
	c0=(c0+t1)&BN_MASK2; if ((c0) < t1) t2++; \
sl@0
   527
	c1=(c1+t2)&BN_MASK2; if ((c1) < t2) c2++;
sl@0
   528
sl@0
   529
#define mul_add_c2(a,b,c0,c1,c2) \
sl@0
   530
	t1=LBITS(a); t2=HBITS(a); \
sl@0
   531
	bl=LBITS(b); bh=HBITS(b); \
sl@0
   532
	mul64(t1,t2,bl,bh); \
sl@0
   533
	if (t2 & BN_TBIT) c2++; \
sl@0
   534
	t2=(t2+t2)&BN_MASK2; \
sl@0
   535
	if (t1 & BN_TBIT) t2++; \
sl@0
   536
	t1=(t1+t1)&BN_MASK2; \
sl@0
   537
	c0=(c0+t1)&BN_MASK2;  \
sl@0
   538
	if ((c0 < t1) && (((++t2)&BN_MASK2) == 0)) c2++; \
sl@0
   539
	c1=(c1+t2)&BN_MASK2; if ((c1) < t2) c2++;
sl@0
   540
sl@0
   541
#define sqr_add_c(a,i,c0,c1,c2) \
sl@0
   542
	sqr64(t1,t2,(a)[i]); \
sl@0
   543
	c0=(c0+t1)&BN_MASK2; if ((c0) < t1) t2++; \
sl@0
   544
	c1=(c1+t2)&BN_MASK2; if ((c1) < t2) c2++;
sl@0
   545
sl@0
   546
#define sqr_add_c2(a,i,j,c0,c1,c2) \
sl@0
   547
	mul_add_c2((a)[i],(a)[j],c0,c1,c2)
sl@0
   548
#endif /* !BN_LLONG */
sl@0
   549
sl@0
   550
EXPORT_C void bn_mul_comba8(BN_ULONG *r, BN_ULONG *a, BN_ULONG *b)
sl@0
   551
	{
sl@0
   552
#ifdef BN_LLONG
sl@0
   553
	BN_ULLONG t;
sl@0
   554
#else
sl@0
   555
	BN_ULONG bl,bh;
sl@0
   556
#endif
sl@0
   557
	BN_ULONG t1,t2;
sl@0
   558
	BN_ULONG c1,c2,c3;
sl@0
   559
sl@0
   560
	c1=0;
sl@0
   561
	c2=0;
sl@0
   562
	c3=0;
sl@0
   563
	mul_add_c(a[0],b[0],c1,c2,c3);
sl@0
   564
	r[0]=c1;
sl@0
   565
	c1=0;
sl@0
   566
	mul_add_c(a[0],b[1],c2,c3,c1);
sl@0
   567
	mul_add_c(a[1],b[0],c2,c3,c1);
sl@0
   568
	r[1]=c2;
sl@0
   569
	c2=0;
sl@0
   570
	mul_add_c(a[2],b[0],c3,c1,c2);
sl@0
   571
	mul_add_c(a[1],b[1],c3,c1,c2);
sl@0
   572
	mul_add_c(a[0],b[2],c3,c1,c2);
sl@0
   573
	r[2]=c3;
sl@0
   574
	c3=0;
sl@0
   575
	mul_add_c(a[0],b[3],c1,c2,c3);
sl@0
   576
	mul_add_c(a[1],b[2],c1,c2,c3);
sl@0
   577
	mul_add_c(a[2],b[1],c1,c2,c3);
sl@0
   578
	mul_add_c(a[3],b[0],c1,c2,c3);
sl@0
   579
	r[3]=c1;
sl@0
   580
	c1=0;
sl@0
   581
	mul_add_c(a[4],b[0],c2,c3,c1);
sl@0
   582
	mul_add_c(a[3],b[1],c2,c3,c1);
sl@0
   583
	mul_add_c(a[2],b[2],c2,c3,c1);
sl@0
   584
	mul_add_c(a[1],b[3],c2,c3,c1);
sl@0
   585
	mul_add_c(a[0],b[4],c2,c3,c1);
sl@0
   586
	r[4]=c2;
sl@0
   587
	c2=0;
sl@0
   588
	mul_add_c(a[0],b[5],c3,c1,c2);
sl@0
   589
	mul_add_c(a[1],b[4],c3,c1,c2);
sl@0
   590
	mul_add_c(a[2],b[3],c3,c1,c2);
sl@0
   591
	mul_add_c(a[3],b[2],c3,c1,c2);
sl@0
   592
	mul_add_c(a[4],b[1],c3,c1,c2);
sl@0
   593
	mul_add_c(a[5],b[0],c3,c1,c2);
sl@0
   594
	r[5]=c3;
sl@0
   595
	c3=0;
sl@0
   596
	mul_add_c(a[6],b[0],c1,c2,c3);
sl@0
   597
	mul_add_c(a[5],b[1],c1,c2,c3);
sl@0
   598
	mul_add_c(a[4],b[2],c1,c2,c3);
sl@0
   599
	mul_add_c(a[3],b[3],c1,c2,c3);
sl@0
   600
	mul_add_c(a[2],b[4],c1,c2,c3);
sl@0
   601
	mul_add_c(a[1],b[5],c1,c2,c3);
sl@0
   602
	mul_add_c(a[0],b[6],c1,c2,c3);
sl@0
   603
	r[6]=c1;
sl@0
   604
	c1=0;
sl@0
   605
	mul_add_c(a[0],b[7],c2,c3,c1);
sl@0
   606
	mul_add_c(a[1],b[6],c2,c3,c1);
sl@0
   607
	mul_add_c(a[2],b[5],c2,c3,c1);
sl@0
   608
	mul_add_c(a[3],b[4],c2,c3,c1);
sl@0
   609
	mul_add_c(a[4],b[3],c2,c3,c1);
sl@0
   610
	mul_add_c(a[5],b[2],c2,c3,c1);
sl@0
   611
	mul_add_c(a[6],b[1],c2,c3,c1);
sl@0
   612
	mul_add_c(a[7],b[0],c2,c3,c1);
sl@0
   613
	r[7]=c2;
sl@0
   614
	c2=0;
sl@0
   615
	mul_add_c(a[7],b[1],c3,c1,c2);
sl@0
   616
	mul_add_c(a[6],b[2],c3,c1,c2);
sl@0
   617
	mul_add_c(a[5],b[3],c3,c1,c2);
sl@0
   618
	mul_add_c(a[4],b[4],c3,c1,c2);
sl@0
   619
	mul_add_c(a[3],b[5],c3,c1,c2);
sl@0
   620
	mul_add_c(a[2],b[6],c3,c1,c2);
sl@0
   621
	mul_add_c(a[1],b[7],c3,c1,c2);
sl@0
   622
	r[8]=c3;
sl@0
   623
	c3=0;
sl@0
   624
	mul_add_c(a[2],b[7],c1,c2,c3);
sl@0
   625
	mul_add_c(a[3],b[6],c1,c2,c3);
sl@0
   626
	mul_add_c(a[4],b[5],c1,c2,c3);
sl@0
   627
	mul_add_c(a[5],b[4],c1,c2,c3);
sl@0
   628
	mul_add_c(a[6],b[3],c1,c2,c3);
sl@0
   629
	mul_add_c(a[7],b[2],c1,c2,c3);
sl@0
   630
	r[9]=c1;
sl@0
   631
	c1=0;
sl@0
   632
	mul_add_c(a[7],b[3],c2,c3,c1);
sl@0
   633
	mul_add_c(a[6],b[4],c2,c3,c1);
sl@0
   634
	mul_add_c(a[5],b[5],c2,c3,c1);
sl@0
   635
	mul_add_c(a[4],b[6],c2,c3,c1);
sl@0
   636
	mul_add_c(a[3],b[7],c2,c3,c1);
sl@0
   637
	r[10]=c2;
sl@0
   638
	c2=0;
sl@0
   639
	mul_add_c(a[4],b[7],c3,c1,c2);
sl@0
   640
	mul_add_c(a[5],b[6],c3,c1,c2);
sl@0
   641
	mul_add_c(a[6],b[5],c3,c1,c2);
sl@0
   642
	mul_add_c(a[7],b[4],c3,c1,c2);
sl@0
   643
	r[11]=c3;
sl@0
   644
	c3=0;
sl@0
   645
	mul_add_c(a[7],b[5],c1,c2,c3);
sl@0
   646
	mul_add_c(a[6],b[6],c1,c2,c3);
sl@0
   647
	mul_add_c(a[5],b[7],c1,c2,c3);
sl@0
   648
	r[12]=c1;
sl@0
   649
	c1=0;
sl@0
   650
	mul_add_c(a[6],b[7],c2,c3,c1);
sl@0
   651
	mul_add_c(a[7],b[6],c2,c3,c1);
sl@0
   652
	r[13]=c2;
sl@0
   653
	c2=0;
sl@0
   654
	mul_add_c(a[7],b[7],c3,c1,c2);
sl@0
   655
	r[14]=c3;
sl@0
   656
	r[15]=c1;
sl@0
   657
	}
sl@0
   658
sl@0
   659
EXPORT_C void bn_mul_comba4(BN_ULONG *r, BN_ULONG *a, BN_ULONG *b)
sl@0
   660
	{
sl@0
   661
#ifdef BN_LLONG
sl@0
   662
	BN_ULLONG t;
sl@0
   663
#else
sl@0
   664
	BN_ULONG bl,bh;
sl@0
   665
#endif
sl@0
   666
	BN_ULONG t1,t2;
sl@0
   667
	BN_ULONG c1,c2,c3;
sl@0
   668
sl@0
   669
	c1=0;
sl@0
   670
	c2=0;
sl@0
   671
	c3=0;
sl@0
   672
	mul_add_c(a[0],b[0],c1,c2,c3);
sl@0
   673
	r[0]=c1;
sl@0
   674
	c1=0;
sl@0
   675
	mul_add_c(a[0],b[1],c2,c3,c1);
sl@0
   676
	mul_add_c(a[1],b[0],c2,c3,c1);
sl@0
   677
	r[1]=c2;
sl@0
   678
	c2=0;
sl@0
   679
	mul_add_c(a[2],b[0],c3,c1,c2);
sl@0
   680
	mul_add_c(a[1],b[1],c3,c1,c2);
sl@0
   681
	mul_add_c(a[0],b[2],c3,c1,c2);
sl@0
   682
	r[2]=c3;
sl@0
   683
	c3=0;
sl@0
   684
	mul_add_c(a[0],b[3],c1,c2,c3);
sl@0
   685
	mul_add_c(a[1],b[2],c1,c2,c3);
sl@0
   686
	mul_add_c(a[2],b[1],c1,c2,c3);
sl@0
   687
	mul_add_c(a[3],b[0],c1,c2,c3);
sl@0
   688
	r[3]=c1;
sl@0
   689
	c1=0;
sl@0
   690
	mul_add_c(a[3],b[1],c2,c3,c1);
sl@0
   691
	mul_add_c(a[2],b[2],c2,c3,c1);
sl@0
   692
	mul_add_c(a[1],b[3],c2,c3,c1);
sl@0
   693
	r[4]=c2;
sl@0
   694
	c2=0;
sl@0
   695
	mul_add_c(a[2],b[3],c3,c1,c2);
sl@0
   696
	mul_add_c(a[3],b[2],c3,c1,c2);
sl@0
   697
	r[5]=c3;
sl@0
   698
	c3=0;
sl@0
   699
	mul_add_c(a[3],b[3],c1,c2,c3);
sl@0
   700
	r[6]=c1;
sl@0
   701
	r[7]=c2;
sl@0
   702
	}
sl@0
   703
sl@0
   704
EXPORT_C void bn_sqr_comba8(BN_ULONG *r, const BN_ULONG *a)
sl@0
   705
	{
sl@0
   706
#ifdef BN_LLONG
sl@0
   707
	BN_ULLONG t,tt;
sl@0
   708
#else
sl@0
   709
	BN_ULONG bl,bh;
sl@0
   710
#endif
sl@0
   711
	BN_ULONG t1,t2;
sl@0
   712
	BN_ULONG c1,c2,c3;
sl@0
   713
sl@0
   714
	c1=0;
sl@0
   715
	c2=0;
sl@0
   716
	c3=0;
sl@0
   717
	sqr_add_c(a,0,c1,c2,c3);
sl@0
   718
	r[0]=c1;
sl@0
   719
	c1=0;
sl@0
   720
	sqr_add_c2(a,1,0,c2,c3,c1);
sl@0
   721
	r[1]=c2;
sl@0
   722
	c2=0;
sl@0
   723
	sqr_add_c(a,1,c3,c1,c2);
sl@0
   724
	sqr_add_c2(a,2,0,c3,c1,c2);
sl@0
   725
	r[2]=c3;
sl@0
   726
	c3=0;
sl@0
   727
	sqr_add_c2(a,3,0,c1,c2,c3);
sl@0
   728
	sqr_add_c2(a,2,1,c1,c2,c3);
sl@0
   729
	r[3]=c1;
sl@0
   730
	c1=0;
sl@0
   731
	sqr_add_c(a,2,c2,c3,c1);
sl@0
   732
	sqr_add_c2(a,3,1,c2,c3,c1);
sl@0
   733
	sqr_add_c2(a,4,0,c2,c3,c1);
sl@0
   734
	r[4]=c2;
sl@0
   735
	c2=0;
sl@0
   736
	sqr_add_c2(a,5,0,c3,c1,c2);
sl@0
   737
	sqr_add_c2(a,4,1,c3,c1,c2);
sl@0
   738
	sqr_add_c2(a,3,2,c3,c1,c2);
sl@0
   739
	r[5]=c3;
sl@0
   740
	c3=0;
sl@0
   741
	sqr_add_c(a,3,c1,c2,c3);
sl@0
   742
	sqr_add_c2(a,4,2,c1,c2,c3);
sl@0
   743
	sqr_add_c2(a,5,1,c1,c2,c3);
sl@0
   744
	sqr_add_c2(a,6,0,c1,c2,c3);
sl@0
   745
	r[6]=c1;
sl@0
   746
	c1=0;
sl@0
   747
	sqr_add_c2(a,7,0,c2,c3,c1);
sl@0
   748
	sqr_add_c2(a,6,1,c2,c3,c1);
sl@0
   749
	sqr_add_c2(a,5,2,c2,c3,c1);
sl@0
   750
	sqr_add_c2(a,4,3,c2,c3,c1);
sl@0
   751
	r[7]=c2;
sl@0
   752
	c2=0;
sl@0
   753
	sqr_add_c(a,4,c3,c1,c2);
sl@0
   754
	sqr_add_c2(a,5,3,c3,c1,c2);
sl@0
   755
	sqr_add_c2(a,6,2,c3,c1,c2);
sl@0
   756
	sqr_add_c2(a,7,1,c3,c1,c2);
sl@0
   757
	r[8]=c3;
sl@0
   758
	c3=0;
sl@0
   759
	sqr_add_c2(a,7,2,c1,c2,c3);
sl@0
   760
	sqr_add_c2(a,6,3,c1,c2,c3);
sl@0
   761
	sqr_add_c2(a,5,4,c1,c2,c3);
sl@0
   762
	r[9]=c1;
sl@0
   763
	c1=0;
sl@0
   764
	sqr_add_c(a,5,c2,c3,c1);
sl@0
   765
	sqr_add_c2(a,6,4,c2,c3,c1);
sl@0
   766
	sqr_add_c2(a,7,3,c2,c3,c1);
sl@0
   767
	r[10]=c2;
sl@0
   768
	c2=0;
sl@0
   769
	sqr_add_c2(a,7,4,c3,c1,c2);
sl@0
   770
	sqr_add_c2(a,6,5,c3,c1,c2);
sl@0
   771
	r[11]=c3;
sl@0
   772
	c3=0;
sl@0
   773
	sqr_add_c(a,6,c1,c2,c3);
sl@0
   774
	sqr_add_c2(a,7,5,c1,c2,c3);
sl@0
   775
	r[12]=c1;
sl@0
   776
	c1=0;
sl@0
   777
	sqr_add_c2(a,7,6,c2,c3,c1);
sl@0
   778
	r[13]=c2;
sl@0
   779
	c2=0;
sl@0
   780
	sqr_add_c(a,7,c3,c1,c2);
sl@0
   781
	r[14]=c3;
sl@0
   782
	r[15]=c1;
sl@0
   783
	}
sl@0
   784
sl@0
   785
EXPORT_C void bn_sqr_comba4(BN_ULONG *r, const BN_ULONG *a)
sl@0
   786
	{
sl@0
   787
#ifdef BN_LLONG
sl@0
   788
	BN_ULLONG t,tt;
sl@0
   789
#else
sl@0
   790
	BN_ULONG bl,bh;
sl@0
   791
#endif
sl@0
   792
	BN_ULONG t1,t2;
sl@0
   793
	BN_ULONG c1,c2,c3;
sl@0
   794
sl@0
   795
	c1=0;
sl@0
   796
	c2=0;
sl@0
   797
	c3=0;
sl@0
   798
	sqr_add_c(a,0,c1,c2,c3);
sl@0
   799
	r[0]=c1;
sl@0
   800
	c1=0;
sl@0
   801
	sqr_add_c2(a,1,0,c2,c3,c1);
sl@0
   802
	r[1]=c2;
sl@0
   803
	c2=0;
sl@0
   804
	sqr_add_c(a,1,c3,c1,c2);
sl@0
   805
	sqr_add_c2(a,2,0,c3,c1,c2);
sl@0
   806
	r[2]=c3;
sl@0
   807
	c3=0;
sl@0
   808
	sqr_add_c2(a,3,0,c1,c2,c3);
sl@0
   809
	sqr_add_c2(a,2,1,c1,c2,c3);
sl@0
   810
	r[3]=c1;
sl@0
   811
	c1=0;
sl@0
   812
	sqr_add_c(a,2,c2,c3,c1);
sl@0
   813
	sqr_add_c2(a,3,1,c2,c3,c1);
sl@0
   814
	r[4]=c2;
sl@0
   815
	c2=0;
sl@0
   816
	sqr_add_c2(a,3,2,c3,c1,c2);
sl@0
   817
	r[5]=c3;
sl@0
   818
	c3=0;
sl@0
   819
	sqr_add_c(a,3,c1,c2,c3);
sl@0
   820
	r[6]=c1;
sl@0
   821
	r[7]=c2;
sl@0
   822
	}
sl@0
   823
#else /* !BN_MUL_COMBA */
sl@0
   824
sl@0
   825
/* hmm... is it faster just to do a multiply? */
sl@0
   826
#undef bn_sqr_comba4
sl@0
   827
EXPORT_C void bn_sqr_comba4(BN_ULONG *r, BN_ULONG *a)
sl@0
   828
	{
sl@0
   829
	BN_ULONG t[8];
sl@0
   830
	bn_sqr_normal(r,a,4,t);
sl@0
   831
	}
sl@0
   832
sl@0
   833
#undef bn_sqr_comba8
sl@0
   834
EXPORT_C void bn_sqr_comba8(BN_ULONG *r, BN_ULONG *a)
sl@0
   835
	{
sl@0
   836
	BN_ULONG t[16];
sl@0
   837
	bn_sqr_normal(r,a,8,t);
sl@0
   838
	}
sl@0
   839
sl@0
   840
EXPORT_C void bn_mul_comba4(BN_ULONG *r, BN_ULONG *a, BN_ULONG *b)
sl@0
   841
	{
sl@0
   842
	r[4]=bn_mul_words(    &(r[0]),a,4,b[0]);
sl@0
   843
	r[5]=bn_mul_add_words(&(r[1]),a,4,b[1]);
sl@0
   844
	r[6]=bn_mul_add_words(&(r[2]),a,4,b[2]);
sl@0
   845
	r[7]=bn_mul_add_words(&(r[3]),a,4,b[3]);
sl@0
   846
	}
sl@0
   847
sl@0
   848
EXPORT_C void bn_mul_comba8(BN_ULONG *r, BN_ULONG *a, BN_ULONG *b)
sl@0
   849
	{
sl@0
   850
	r[ 8]=bn_mul_words(    &(r[0]),a,8,b[0]);
sl@0
   851
	r[ 9]=bn_mul_add_words(&(r[1]),a,8,b[1]);
sl@0
   852
	r[10]=bn_mul_add_words(&(r[2]),a,8,b[2]);
sl@0
   853
	r[11]=bn_mul_add_words(&(r[3]),a,8,b[3]);
sl@0
   854
	r[12]=bn_mul_add_words(&(r[4]),a,8,b[4]);
sl@0
   855
	r[13]=bn_mul_add_words(&(r[5]),a,8,b[5]);
sl@0
   856
	r[14]=bn_mul_add_words(&(r[6]),a,8,b[6]);
sl@0
   857
	r[15]=bn_mul_add_words(&(r[7]),a,8,b[7]);
sl@0
   858
	}
sl@0
   859
sl@0
   860
#endif /* !BN_MUL_COMBA */