From 1f283cb9b3882561aef6b03460e5a202c9e7b91a Mon Sep 17 00:00:00 2001
From: "[GGSuchao]" <[1500062807@pku.edu.cn]>
Date: Mon, 10 Jul 2017 10:19:34 +0800
Subject: [PATCH] update sm_standard
---
crypto/sm2/build.info | 6 +-
crypto/sm2/miracl/mralloc.c | 85 --
crypto/sm2/miracl/mrarth0.c | 320 ----
crypto/sm2/miracl/mrarth1.c | 1068 --------------
crypto/sm2/miracl/mrarth2.c | 1584 --------------------
crypto/sm2/miracl/mrarth3.c | 231 ---
crypto/sm2/miracl/mrbits.c | 245 ----
crypto/sm2/miracl/mrcore.c | 2290 -----------------------------
crypto/sm2/miracl/mrcurve.c | 2507 --------------------------------
crypto/sm2/miracl/mrjack.c | 342 -----
crypto/sm2/miracl/mrlucas.c | 157 --
crypto/sm2/miracl/mrmonty.c | 1414 ------------------
crypto/sm2/miracl/mrmuldv.c | 59 -
crypto/sm2/miracl/mrsroot.c | 188 ---
crypto/sm2/miracl/mrxgcd.c | 495 -------
crypto/sm2/sm2_standard_enc.c | 253 ----
crypto/sm2/sm2_standard_exch.c | 491 -------
crypto/sm2/sm2_standard_sign.c | 349 -----
18 files changed, 1 insertion(+), 12083 deletions(-)
delete mode 100644 crypto/sm2/miracl/mralloc.c
delete mode 100644 crypto/sm2/miracl/mrarth0.c
delete mode 100644 crypto/sm2/miracl/mrarth1.c
delete mode 100644 crypto/sm2/miracl/mrarth2.c
delete mode 100644 crypto/sm2/miracl/mrarth3.c
delete mode 100644 crypto/sm2/miracl/mrbits.c
delete mode 100644 crypto/sm2/miracl/mrcore.c
delete mode 100644 crypto/sm2/miracl/mrcurve.c
delete mode 100644 crypto/sm2/miracl/mrjack.c
delete mode 100644 crypto/sm2/miracl/mrlucas.c
delete mode 100644 crypto/sm2/miracl/mrmonty.c
delete mode 100644 crypto/sm2/miracl/mrmuldv.c
delete mode 100644 crypto/sm2/miracl/mrsroot.c
delete mode 100644 crypto/sm2/miracl/mrxgcd.c
delete mode 100644 crypto/sm2/sm2_standard_enc.c
delete mode 100644 crypto/sm2/sm2_standard_exch.c
delete mode 100644 crypto/sm2/sm2_standard_sign.c
diff --git a/crypto/sm2/build.info b/crypto/sm2/build.info
index d87944c2..5ac994bc 100644
--- a/crypto/sm2/build.info
+++ b/crypto/sm2/build.info
@@ -1,7 +1,3 @@
LIBS=../../libcrypto
SOURCE[../../libcrypto]=sm2_err.c sm2_asn1.c sm2_id.c sm2_sign.c sm2_enc.c \
- sm2_oct.c sm2_exch.c sm2_kmeth.c sm2_standard_enc.c sm2_standard_exch.c \
- sm2_standard_sign.c ./miracl/mralloc.c ./miracl/mrarth0.c \
- ./miracl/mrarth1.c ./miracl/mrarth2.c ./miracl/mrarth3.c ./miracl/mrbits.c \
- ./miracl/mrcore.c ./miracl/mrcurve.c ./miracl/mrjack.c ./miracl/mrlucas.c\
- ./miracl/mrmonty.c ./miracl/mrmuldv.c ./miracl/mrsroot.c ./miracl/mrxgcd.c
+ sm2_oct.c sm2_exch.c sm2_kmeth.c \
diff --git a/crypto/sm2/miracl/mralloc.c b/crypto/sm2/miracl/mralloc.c
deleted file mode 100644
index f3855ad5..00000000
--- a/crypto/sm2/miracl/mralloc.c
+++ /dev/null
@@ -1,85 +0,0 @@
-
-/***************************************************************************
- *
-Copyright 2013 CertiVox IOM Ltd. *
- *
-This file is part of CertiVox MIRACL Crypto SDK. *
- *
-The CertiVox MIRACL Crypto SDK provides developers with an *
-extensive and efficient set of cryptographic functions. *
-For further information about its features and functionalities please *
-refer to http://www.certivox.com *
- *
-* The CertiVox MIRACL Crypto SDK is free software: you can *
- redistribute it and/or modify it under the terms of the *
- GNU Affero General Public License as published by the *
- Free Software Foundation, either version 3 of the License, *
- or (at your option) any later version. *
- *
-* The CertiVox MIRACL Crypto SDK is distributed in the hope *
- that it will be useful, but WITHOUT ANY WARRANTY; without even the *
- implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. *
- See the GNU Affero General Public License for more details. *
- *
-* You should have received a copy of the GNU Affero General Public *
- License along with CertiVox MIRACL Crypto SDK. *
- If not, see . *
- *
-You can be released from the requirements of the license by purchasing *
-a commercial license. Buying such a license is mandatory as soon as you *
-develop commercial activities involving the CertiVox MIRACL Crypto SDK *
-without disclosing the source code of your own applications, or shipping *
-the CertiVox MIRACL Crypto SDK with a closed source product. *
- *
-***************************************************************************/
-/*
- * MIRACL memory allocation routines
- * mralloc.c
- *
- * MIRACL C Memory allocation/deallocation
- * Can be replaced with special user-defined routines
- * Default is to standard system routines
- *
- * NOTE: uses calloc() which initialises memory to Zero, so make sure
- * any substituted routine does the same!
- */
-
-#include
-#include
-
-#ifndef MR_STATIC
-
-miracl *mr_first_alloc()
-{
- return (miracl *)calloc(1,sizeof(miracl));
-}
-
-void *mr_alloc(_MIPD_ int num,int size)
-{
- char *p;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- if (mr_mip==NULL)
- {
- p=(char *)calloc(num,size);
- return (void *)p;
- }
-
- if (mr_mip->ERNUM) return NULL;
-
- p=(char *)calloc(num,size);
- if (p==NULL) mr_berror(_MIPP_ MR_ERR_OUT_OF_MEMORY);
- return (void *)p;
-
-}
-
-void mr_free(void *addr)
-{
- if (addr==NULL) return;
- free(addr);
- return;
-}
-
-#endif
diff --git a/crypto/sm2/miracl/mrarth0.c b/crypto/sm2/miracl/mrarth0.c
deleted file mode 100644
index 2016a1d4..00000000
--- a/crypto/sm2/miracl/mrarth0.c
+++ /dev/null
@@ -1,320 +0,0 @@
-
-/***************************************************************************
- *
-Copyright 2013 CertiVox IOM Ltd. *
- *
-This file is part of CertiVox MIRACL Crypto SDK. *
- *
-The CertiVox MIRACL Crypto SDK provides developers with an *
-extensive and efficient set of cryptographic functions. *
-For further information about its features and functionalities please *
-refer to http://www.certivox.com *
- *
-* The CertiVox MIRACL Crypto SDK is free software: you can *
- redistribute it and/or modify it under the terms of the *
- GNU Affero General Public License as published by the *
- Free Software Foundation, either version 3 of the License, *
- or (at your option) any later version. *
- *
-* The CertiVox MIRACL Crypto SDK is distributed in the hope *
- that it will be useful, but WITHOUT ANY WARRANTY; without even the *
- implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. *
- See the GNU Affero General Public License for more details. *
- *
-* You should have received a copy of the GNU Affero General Public *
- License along with CertiVox MIRACL Crypto SDK. *
- If not, see . *
- *
-You can be released from the requirements of the license by purchasing *
-a commercial license. Buying such a license is mandatory as soon as you *
-develop commercial activities involving the CertiVox MIRACL Crypto SDK *
-without disclosing the source code of your own applications, or shipping *
-the CertiVox MIRACL Crypto SDK with a closed source product. *
- *
-***************************************************************************/
-/*
- * MIRACL arithmetic routines 0 - Add and subtract routines
- * mrarth0.c
- *
- */
-#include
-
-void mr_padd(_MIPD_ big x,big y,big z)
-{ /* add two big numbers, z=x+y where *
- * x and y are positive */
- int i,lx,ly,lz,la;
- mr_small carry,psum;
- mr_small *gx,*gy,*gz;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- lx = (int)x->len;
- ly = (int)y->len;
-
- if (ly>lx)
- {
- lz=ly;
- la=lx;
- if (x!=z) copy(y,z);
- else la=ly;
- }
- else
- {
- lz=lx;
- la=ly;
- if (y!=z) copy(x,z);
- else la=lx;
- }
- carry=0;
- z->len=lz;
- gx=x->w; gy=y->w; gz=z->w;
- if (lznib || !mr_mip->check) z->len++;
-#ifndef MR_SIMPLE_BASE
- if (mr_mip->base==0)
- {
-#endif
- for (i=0;igx[i]) carry=0;
- else if (psum0;i++ )
- { /* add by columns to the length of larger number (if there is a carry) */
- psum=gx[i]+gy[i]+carry;
- if (psum>gx[i]) carry=0;
- else if (psumcheck && i>=mr_mip->nib)
- {
- mr_berror(_MIPP_ MR_ERR_OVERFLOW);
- return;
- }
- gz[i]=carry;
- }
-#ifndef MR_SIMPLE_BASE
- }
- else
- {
- for (i=0;i=mr_mip->base)
- { /* set carry */
- carry=1;
- psum-=mr_mip->base;
- }
- gz[i]=psum;
- }
- for (;i0;i++)
- {
- psum=gx[i]+gy[i]+carry;
- carry=0;
- if (psum>=mr_mip->base)
- { /* set carry */
- carry=1;
- psum-=mr_mip->base;
- }
- gz[i]=psum;
- }
- if (carry)
- { /* carry left over - possible overflow */
- if (mr_mip->check && i>=mr_mip->nib)
- {
- mr_berror(_MIPP_ MR_ERR_OVERFLOW);
- return;
- }
- gz[i]=carry;
- }
- }
-#endif
- if (gz[z->len-1]==0) z->len--;
-
-}
-
-void mr_psub(_MIPD_ big x,big y,big z)
-{ /* subtract two big numbers z=x-y *
- * where x and y are positive and x>y */
- int i,lx,ly;
- mr_small borrow,pdiff;
- mr_small *gx,*gy,*gz;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- lx = (int)x->len;
- ly = (int)y->len;
- if (ly>lx)
- {
- mr_berror(_MIPP_ MR_ERR_NEG_RESULT);
- return;
- }
- if (y!=z) copy(x,z);
- else ly=lx;
- z->len=lx;
- gx=x->w; gy=y->w; gz=z->w;
- borrow=0;
-#ifndef MR_SIMPLE_BASE
- if (mr_mip->base==0)
- {
-#endif
- for (i=0;i0;i++)
- { /* subtract by columns */
- if (i>lx)
- {
- mr_berror(_MIPP_ MR_ERR_NEG_RESULT);
- return;
- }
- pdiff=gx[i]-gy[i]-borrow;
- if (pdiffgx[i]) borrow=1;
- gz[i]=pdiff;
- }
-#ifndef MR_SIMPLE_BASE
- }
- else for (i=0;i0;i++)
- { /* subtract by columns */
- if (i>lx)
- {
- mr_berror(_MIPP_ MR_ERR_NEG_RESULT);
- return;
- }
- pdiff=gy[i]+borrow;
- borrow=0;
- if (gx[i]>=pdiff) pdiff=gx[i]-pdiff;
- else
- { /* set borrow */
- pdiff=mr_mip->base+gx[i]-pdiff;
- borrow=1;
- }
- gz[i]=pdiff;
- }
-#endif
- mr_lzero(z);
-}
-
-static void mr_select(_MIPD_ big x,int d,big y,big z)
-{ /* perform required add or subtract operation */
- int sx,sy,sz,jf,xgty;
-#ifdef MR_FLASH
- if (mr_notint(x) || mr_notint(y))
- {
- mr_berror(_MIPP_ MR_ERR_INT_OP);
- return;
- }
-#endif
- sx=exsign(x);
- sy=exsign(y);
- sz=0;
- x->len&=MR_OBITS; /* force operands to be positive */
- y->len&=MR_OBITS;
- xgty=mr_compare(x,y);
- jf=(1+sx)+(1+d*sy)/2;
- switch (jf)
- { /* branch according to signs of operands */
- case 0:
- if (xgty>=0)
- mr_padd(_MIPP_ x,y,z);
- else
- mr_padd(_MIPP_ y,x,z);
- sz=MINUS;
- break;
- case 1:
- if (xgty<=0)
- {
- mr_psub(_MIPP_ y,x,z);
- sz=PLUS;
- }
- else
- {
- mr_psub(_MIPP_ x,y,z);
- sz=MINUS;
- }
- break;
- case 2:
- if (xgty>=0)
- {
- mr_psub(_MIPP_ x,y,z);
- sz=PLUS;
- }
- else
- {
- mr_psub(_MIPP_ y,x,z);
- sz=MINUS;
- }
- break;
- case 3:
- if (xgty>=0)
- mr_padd(_MIPP_ x,y,z);
- else
- mr_padd(_MIPP_ y,x,z);
- sz=PLUS;
- break;
- }
- if (sz<0) z->len^=MR_MSBIT; /* set sign of result */
- if (x!=z && sx<0) x->len^=MR_MSBIT; /* restore signs to operands */
- if (y!=z && y!=x && sy<0) y->len^=MR_MSBIT;
-}
-
-void add(_MIPD_ big x,big y,big z)
-{ /* add two signed big numbers together z=x+y */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(27)
-
- mr_select(_MIPP_ x,PLUS,y,z);
-
- MR_OUT
-}
-
-void subtract(_MIPD_ big x,big y,big z)
-{ /* subtract two big signed numbers z=x-y */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(28)
-
- mr_select(_MIPP_ x,MINUS,y,z);
-
- MR_OUT
-}
-
-void incr(_MIPD_ big x,int n,big z)
-{ /* add int to big number: z=x+n */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(7)
-
- convert(_MIPP_ n,mr_mip->w0);
- mr_select(_MIPP_ x,PLUS,mr_mip->w0,z);
-
- MR_OUT
-}
-
-void decr(_MIPD_ big x,int n,big z)
-{ /* subtract int from big number: z=x-n */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(8)
-
- convert(_MIPP_ n,mr_mip->w0);
- mr_select(_MIPP_ x,MINUS,mr_mip->w0,z);
-
- MR_OUT
-}
-
diff --git a/crypto/sm2/miracl/mrarth1.c b/crypto/sm2/miracl/mrarth1.c
deleted file mode 100644
index f43b798a..00000000
--- a/crypto/sm2/miracl/mrarth1.c
+++ /dev/null
@@ -1,1068 +0,0 @@
-
-/***************************************************************************
- *
-Copyright 2013 CertiVox IOM Ltd. *
- *
-This file is part of CertiVox MIRACL Crypto SDK. *
- *
-The CertiVox MIRACL Crypto SDK provides developers with an *
-extensive and efficient set of cryptographic functions. *
-For further information about its features and functionalities please *
-refer to http://www.certivox.com *
- *
-* The CertiVox MIRACL Crypto SDK is free software: you can *
- redistribute it and/or modify it under the terms of the *
- GNU Affero General Public License as published by the *
- Free Software Foundation, either version 3 of the License, *
- or (at your option) any later version. *
- *
-* The CertiVox MIRACL Crypto SDK is distributed in the hope *
- that it will be useful, but WITHOUT ANY WARRANTY; without even the *
- implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. *
- See the GNU Affero General Public License for more details. *
- *
-* You should have received a copy of the GNU Affero General Public *
- License along with CertiVox MIRACL Crypto SDK. *
- If not, see . *
- *
-You can be released from the requirements of the license by purchasing *
-a commercial license. Buying such a license is mandatory as soon as you *
-develop commercial activities involving the CertiVox MIRACL Crypto SDK *
-without disclosing the source code of your own applications, or shipping *
-the CertiVox MIRACL Crypto SDK with a closed source product. *
- *
-***************************************************************************/
-
-/*
- *
- * MIRACL arithmetic routines 1 - multiplying and dividing BIG NUMBERS by
- * integer numbers.
- * mrarth1.c
- *
- */
-
-#include
-
-#ifdef MR_FP
-#include
-#endif
-
-#ifdef MR_WIN64
-#include
-#endif
-
-#ifdef MR_FP_ROUNDING
-#ifdef __GNUC__
-#include
-#endif
-
-/* Invert n and set FP rounding.
- * Set to round up
- * Calculate 1/n
- * set to round down (towards zero)
- * If rounding cannot be controlled, this function returns 0.0 */
-
-mr_large mr_invert(mr_small n)
-{
- mr_large inn;
- int up= 0x1BFF;
-
-#ifdef _MSC_VER
- #ifdef MR_NOASM
-#define NO_EXTENDED
- #endif
-#endif
-
-#ifdef NO_EXTENDED
- int down=0x1EFF;
-#else
- int down=0x1FFF;
-#endif
-
-#ifdef __TURBOC__
- asm
- {
- fldcw WORD PTR up
- fld1
- fld QWORD PTR n;
- fdiv
- fstp TBYTE PTR inn;
- fldcw WORD PTR down;
- }
- return inn;
-#endif
-#ifdef _MSC_VER
- _asm
- {
- fldcw WORD PTR up
- fld1
- fld QWORD PTR n;
- fdiv
- fstp QWORD PTR inn;
- fldcw WORD PTR down;
- }
- return inn;
-#endif
-#ifdef __GNUC__
-#ifdef i386
- __asm__ __volatile__ (
- "fldcw %2\n"
- "fld1\n"
- "fldl %1\n"
- "fdivrp\n"
- "fstpt %0\n"
- "fldcw %3\n"
- : "=m"(inn)
- : "m"(n),"m"(up),"m"(down)
- : "memory"
- );
- return inn;
-#else
- fpsetround(FP_RP);
- inn=(mr_large)1.0/n;
- fpsetround(FP_RZ);
- return inn;
-#endif
-#endif
- return 0.0L;
-}
-
-#endif
-
-void mr_pmul(_MIPD_ big x,mr_small sn,big z)
-{
- int m,xl;
- mr_lentype sx;
- mr_small carry,*xg,*zg;
-
-#ifdef MR_ITANIUM
- mr_small tm;
-#endif
-#ifdef MR_WIN64
- mr_small tm;
-#endif
-#ifdef MR_NOASM
- union doubleword dble;
- mr_large dbled;
- mr_large ldres;
-#endif
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- if (x!=z)
- {
- zero(z);
- if (sn==0) return;
- }
- else if (sn==0)
- {
- zero(z);
- return;
- }
- m=0;
- carry=0;
- sx=x->len&MR_MSBIT;
- xl=(int)(x->len&MR_OBITS);
-
-#ifndef MR_SIMPLE_BASE
- if (mr_mip->base==0)
- {
-#endif
-#ifndef MR_NOFULLWIDTH
- xg=x->w; zg=z->w;
-/* inline 8086 assembly - substitutes for loop below */
-#ifdef INLINE_ASM
-#if INLINE_ASM == 1
- ASM cld
- ASM mov cx,xl
- ASM or cx,cx
- ASM je out1
-#ifdef MR_LMM
- ASM push ds
- ASM push es
- ASM les di,DWORD PTR zg
- ASM lds si,DWORD PTR xg
-#else
- ASM mov ax,ds
- ASM mov es,ax
- ASM mov di,zg
- ASM mov si,xg
-#endif
- ASM mov bx,sn
- ASM push bp
- ASM xor bp,bp
- tcl1:
- ASM lodsw
- ASM mul bx
- ASM add ax,bp
- ASM adc dx,0
- ASM stosw
- ASM mov bp,dx
- ASM loop tcl1
-
- ASM mov ax,bp
- ASM pop bp
-#ifdef MR_LMM
- ASM pop es
- ASM pop ds
-#endif
- ASM mov carry,ax
- out1:
-#endif
-#if INLINE_ASM == 2
- ASM cld
- ASM mov cx,xl
- ASM or cx,cx
- ASM je out1
-#ifdef MR_LMM
- ASM push ds
- ASM push es
- ASM les di,DWORD PTR zg
- ASM lds si,DWORD PTR xg
-#else
- ASM mov ax,ds
- ASM mov es,ax
- ASM mov di,zg
- ASM mov si,xg
-#endif
- ASM mov ebx,sn
- ASM push ebp
- ASM xor ebp,ebp
- tcl1:
- ASM lodsd
- ASM mul ebx
- ASM add eax,ebp
- ASM adc edx,0
- ASM stosd
- ASM mov ebp,edx
- ASM loop tcl1
-
- ASM mov eax,ebp
- ASM pop ebp
-#ifdef MR_LMM
- ASM pop es
- ASM pop ds
-#endif
- ASM mov carry,eax
- out1:
-#endif
-#if INLINE_ASM == 3
- ASM mov ecx,xl
- ASM or ecx,ecx
- ASM je out1
- ASM mov ebx,sn
- ASM mov edi,zg
- ASM mov esi,xg
- ASM push ebp
- ASM xor ebp,ebp
- tcl1:
- ASM mov eax,[esi]
- ASM add esi,4
- ASM mul ebx
- ASM add eax,ebp
- ASM adc edx,0
- ASM mov [edi],eax
- ASM add edi,4
- ASM mov ebp,edx
- ASM dec ecx
- ASM jnz tcl1
-
- ASM mov eax,ebp
- ASM pop ebp
- ASM mov carry,eax
- out1:
-#endif
-#if INLINE_ASM == 4
-
- ASM (
- "movl %4,%%ecx\n"
- "orl %%ecx,%%ecx\n"
- "je 1f\n"
- "movl %3,%%ebx\n"
- "movl %1,%%edi\n"
- "movl %2,%%esi\n"
- "pushl %%ebp\n"
- "xorl %%ebp,%%ebp\n"
- "0:\n"
- "movl (%%esi),%%eax\n"
- "addl $4,%%esi\n"
- "mull %%ebx\n"
- "addl %%ebp,%%eax\n"
- "adcl $0,%%edx\n"
- "movl %%eax,(%%edi)\n"
- "addl $4,%%edi\n"
- "movl %%edx,%%ebp\n"
- "decl %%ecx\n"
- "jnz 0b\n"
-
- "movl %%ebp,%%eax\n"
- "popl %%ebp\n"
- "movl %%eax,%0\n"
- "1:"
- :"=m"(carry)
- :"m"(zg),"m"(xg),"m"(sn),"m"(xl)
- :"eax","edi","esi","ebx","ecx","edx","memory"
- );
-
-#endif
-#endif
-#ifndef INLINE_ASM
- for (m=0;mw[m]*sn+carry;
- carry=dble.h[MR_TOP];
- z->w[m]=dble.h[MR_BOT];
- }
-#else
- carry=muldvd(x->w[m],sn,carry,&z->w[m]);
-#endif
-#endif
- if (carry>0)
- {
- m=xl;
- if (m>=mr_mip->nib && mr_mip->check)
- {
- mr_berror(_MIPP_ MR_ERR_OVERFLOW);
- return;
- }
- z->w[m]=carry;
- z->len=m+1;
- }
- else z->len=xl;
-#endif
-#ifndef MR_SIMPLE_BASE
- }
- else while (m0)
- { /* multiply each digit of x by n */
-
- if (m>mr_mip->nib && mr_mip->check)
- {
- mr_berror(_MIPP_ MR_ERR_OVERFLOW);
- return;
- }
-#ifdef MR_NOASM
- dbled=(mr_large)x->w[m]*sn+carry;
- #ifdef MR_FP_ROUNDING
- carry=(mr_small)MR_LROUND(dbled*mr_mip->inverse_base);
- #else
- #ifndef MR_FP
- if (mr_mip->base==mr_mip->base2)
- carry=(mr_small)(dbled>>mr_mip->lg2b);
- else
- #endif
- carry=(mr_small)MR_LROUND(dbled/mr_mip->base);
- #endif
- z->w[m]=(mr_small)(dbled-(mr_large)carry*mr_mip->base);
-#else
- #ifdef MR_FP_ROUNDING
- carry=imuldiv(x->w[m],sn,carry,mr_mip->base,mr_mip->inverse_base,&z->w[m]);
- #else
- carry=muldiv(x->w[m],sn,carry,mr_mip->base,&z->w[m]);
- #endif
-#endif
-
- m++;
- z->len=m;
- }
-#endif
- if (z->len!=0) z->len|=sx;
-}
-
-void premult(_MIPD_ big x,int n,big z)
-{ /* premultiply a big number by an int z=x.n */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(9)
-
-
-#ifdef MR_FLASH
- if (mr_notint(x))
- {
- mr_berror(_MIPP_ MR_ERR_INT_OP);
- MR_OUT
- return;
- }
-#endif
- if (n==0) /* test for some special cases */
- {
- zero(z);
- MR_OUT
- return;
- }
- if (n==1)
- {
- copy(x,z);
- MR_OUT
- return;
- }
- if (n<0)
- {
- n=(-n);
- mr_pmul(_MIPP_ x,(mr_small)n,z);
- if (z->len!=0) z->len^=MR_MSBIT;
- }
- else mr_pmul(_MIPP_ x,(mr_small)n,z);
- MR_OUT
-}
-
-#ifdef MR_FP_ROUNDING
-mr_small mr_sdiv(_MIPD_ big x,mr_small sn,mr_large isn,big z)
-#else
-mr_small mr_sdiv(_MIPD_ big x,mr_small sn,big z)
-#endif
-{
- int i,xl;
- mr_small sr,*xg,*zg;
-#ifdef MR_NOASM
- union doubleword dble;
- mr_large dbled;
- mr_large ldres;
-#endif
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- sr=0;
- xl=(int)(x->len&MR_OBITS);
- if (x!=z) zero(z);
-#ifndef MR_SIMPLE_BASE
- if (mr_mip->base==0)
- {
-#endif
-#ifndef MR_NOFULLWIDTH
- xg=x->w; zg=z->w;
-/* inline - substitutes for loop below */
-#ifdef INLINE_ASM
-#if INLINE_ASM == 1
- ASM std
- ASM mov cx,xl
- ASM or cx,cx
- ASM je out2
- ASM mov bx,cx
- ASM shl bx,1
- ASM sub bx,2
-#ifdef MR_LMM
- ASM push ds
- ASM push es
- ASM les di,DWORD PTR zg
- ASM lds si,DWORD PTR xg
-#else
- ASM mov ax,ds
- ASM mov es,ax
- ASM mov di,zg
- ASM mov si,xg
-#endif
- ASM add si,bx
- ASM add di,bx
- ASM mov bx,sn
- ASM push bp
- ASM xor bp,bp
- tcl2:
- ASM mov dx,bp
- ASM lodsw
- ASM div bx
- ASM mov bp,dx
- ASM stosw
- ASM loop tcl2
-
- ASM mov ax,bp
- ASM pop bp
-#ifdef MR_LMM
- ASM pop es
- ASM pop ds
-#endif
- ASM mov sr,ax
- out2:
- ASM cld
-#endif
-#if INLINE_ASM == 2
- ASM std
- ASM mov cx,xl
- ASM or cx,cx
- ASM je out2
- ASM mov bx,cx
- ASM shl bx,2
- ASM sub bx,4
-#ifdef MR_LMM
- ASM push ds
- ASM push es
- ASM les di,DWORD PTR zg
- ASM lds si,DWORD PTR xg
-#else
- ASM mov ax,ds
- ASM mov es,ax
- ASM mov di, zg
- ASM mov si, xg
-#endif
- ASM add si,bx
- ASM add di,bx
- ASM mov ebx,sn
- ASM push ebp
- ASM xor ebp,ebp
- tcl2:
- ASM mov edx,ebp
- ASM lodsd
- ASM div ebx
- ASM mov ebp,edx
- ASM stosd
- ASM loop tcl2
-
- ASM mov eax,ebp
- ASM pop ebp
-#ifdef MR_LMM
- ASM pop es
- ASM pop ds
-#endif
- ASM mov sr,eax
- out2:
- ASM cld
-#endif
-#if INLINE_ASM == 3
- ASM mov ecx,xl
- ASM or ecx,ecx
- ASM je out2
- ASM mov ebx,ecx
- ASM shl ebx,2
- ASM mov esi, xg
- ASM add esi,ebx
- ASM mov edi, zg
- ASM add edi,ebx
- ASM mov ebx,sn
- ASM push ebp
- ASM xor ebp,ebp
- tcl2:
- ASM sub esi,4
- ASM mov edx,ebp
- ASM mov eax,[esi]
- ASM div ebx
- ASM sub edi,4
- ASM mov ebp,edx
- ASM mov [edi],eax
- ASM dec ecx
- ASM jnz tcl2
-
- ASM mov eax,ebp
- ASM pop ebp
- ASM mov sr,eax
- out2:
- ASM nop
-#endif
-#if INLINE_ASM == 4
-
- ASM (
- "movl %4,%%ecx\n"
- "orl %%ecx,%%ecx\n"
- "je 3f\n"
- "movl %%ecx,%%ebx\n"
- "shll $2,%%ebx\n"
- "movl %2,%%esi\n"
- "addl %%ebx,%%esi\n"
- "movl %1,%%edi\n"
- "addl %%ebx,%%edi\n"
- "movl %3,%%ebx\n"
- "pushl %%ebp\n"
- "xorl %%ebp,%%ebp\n"
- "2:\n"
- "subl $4,%%esi\n"
- "movl %%ebp,%%edx\n"
- "movl (%%esi),%%eax\n"
- "divl %%ebx\n"
- "subl $4,%%edi\n"
- "movl %%edx,%%ebp\n"
- "movl %%eax,(%%edi)\n"
- "decl %%ecx\n"
- "jnz 2b\n"
-
- "movl %%ebp,%%eax\n"
- "popl %%ebp\n"
- "movl %%eax,%0\n"
- "3:"
- "nop"
- :"=m"(sr)
- :"m"(zg),"m"(xg),"m"(sn),"m"(xl)
- :"eax","edi","esi","ebx","ecx","edx","memory"
- );
-#endif
-#endif
-#ifndef INLINE_ASM
- for (i=xl-1;i>=0;i--)
- {
-#ifdef MR_NOASM
- dble.h[MR_BOT]=x->w[i];
- dble.h[MR_TOP]=sr;
- z->w[i]=(mr_small)(dble.d/sn);
- sr=(mr_small)(dble.d-(mr_large)z->w[i]*sn);
-#else
- z->w[i]=muldvm(sr,x->w[i],sn,&sr);
-#endif
- }
-#endif
-#endif
-#ifndef MR_SIMPLE_BASE
- }
- else for (i=xl-1;i>=0;i--)
- { /* divide each digit of x by n */
-#ifdef MR_NOASM
- dbled=(mr_large)sr*mr_mip->base+x->w[i];
-#ifdef MR_FP_ROUNDING
- z->w[i]=(mr_small)MR_LROUND(dbled*isn);
-#else
- z->w[i]=(mr_small)MR_LROUND(dbled/sn);
-#endif
- sr=(mr_small)(dbled-(mr_large)z->w[i]*sn);
-#else
-#ifdef MR_FP_ROUNDING
- z->w[i]=imuldiv(sr,mr_mip->base,x->w[i],sn,isn,&sr);
-#else
- z->w[i]=muldiv(sr,mr_mip->base,x->w[i],sn,&sr);
-#endif
-#endif
- }
-#endif
- z->len=x->len;
- mr_lzero(z);
- return sr;
-}
-
-int subdiv(_MIPD_ big x,int n,big z)
-{ /* subdivide a big number by an int z=x/n *
- * returns int remainder */
- mr_lentype sx;
-#ifdef MR_FP_ROUNDING
- mr_large in;
-#endif
- int r,i,msb;
- mr_small lsb;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return 0;
-
- MR_IN(10)
-#ifdef MR_FLASH
- if (mr_notint(x)) mr_berror(_MIPP_ MR_ERR_INT_OP);
-#endif
- if (n==0) mr_berror(_MIPP_ MR_ERR_DIV_BY_ZERO);
- if (mr_mip->ERNUM)
- {
- MR_OUT
- return 0;
- }
-
- if (x->len==0)
- {
- zero(z);
- MR_OUT
- return 0;
- }
- if (n==1) /* special case */
- {
- copy(x,z);
- MR_OUT
- return 0;
- }
- sx=(x->len&MR_MSBIT);
- if (n==2 && mr_mip->base==0)
- { /* fast division by 2 using shifting */
-#ifndef MR_NOFULLWIDTH
-
-/* I don't want this code upsetting the compiler ... */
-/* mr_mip->base==0 can't happen with MR_NOFULLWIDTH */
-
- copy(x,z);
- msb=(int)(z->len&MR_OBITS)-1;
- r=(int)z->w[0]&1;
- for (i=0;;i++)
- {
- z->w[i]>>=1;
- if (i==msb)
- {
- if (z->w[i]==0) mr_lzero(z);
- break;
- }
- lsb=z->w[i+1]&1;
- z->w[i]|=(lsb<<(MIRACL-1));
- }
-
- MR_OUT
- if (sx==0) return r;
- else return (-r);
-#endif
- }
-
-#ifdef MR_FP_ROUNDING
- in=mr_invert(n);
-#endif
- if (n<0)
- {
- n=(-n);
-#ifdef MR_FP_ROUNDING
- r=(int)mr_sdiv(_MIPP_ x,(mr_small)n,in,z);
-#else
- r=(int)mr_sdiv(_MIPP_ x,(mr_small)n,z);
-#endif
- if (z->len!=0) z->len^=MR_MSBIT;
- }
-#ifdef MR_FP_ROUNDING
- else r=(int)mr_sdiv(_MIPP_ x,(mr_small)n,in,z);
-#else
- else r=(int)mr_sdiv(_MIPP_ x,(mr_small)n,z);
-#endif
- MR_OUT
- if (sx==0) return r;
- else return (-r);
-}
-
-int remain(_MIPD_ big x,int n)
-{ /* return integer remainder when x divided by n */
- int r;
- mr_lentype sx;
-#ifdef MR_FP
- mr_small dres;
-#endif
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return FALSE;
-
- MR_IN(88);
-
- sx=(x->len&MR_MSBIT);
-
- if (n==2 && MR_REMAIN(mr_mip->base,2)==0)
- { /* fast odd/even check if base is even */
- MR_OUT
- if ((int)MR_REMAIN(x->w[0],2)==0) return 0;
- else
- {
- if (sx==0) return 1;
- else return (-1);
- }
- }
- if (n==8 && MR_REMAIN(mr_mip->base,8)==0)
- { /* fast check */
- MR_OUT
- r=(int)MR_REMAIN(x->w[0],8);
- if (sx!=0) r=-r;
- return r;
- }
-
- copy(x,mr_mip->w0);
- r=subdiv(_MIPP_ mr_mip->w0,n,mr_mip->w0);
- MR_OUT
- return r;
-}
-
-BOOL subdivisible(_MIPD_ big x,int n)
-{
- if (remain(_MIPP_ x,n)==0) return TRUE;
- else return FALSE;
-}
-
-int hamming(_MIPD_ big x)
-{
- int h;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return 0;
- MR_IN(148);
- h=0;
- copy(x,mr_mip->w1);
- absol(mr_mip->w1,mr_mip->w1);
- while (size(mr_mip->w1)!=0)
- h+=subdiv(_MIPP_ mr_mip->w1,2,mr_mip->w1);
-
- MR_OUT
- return h;
-}
-
-void bytes_to_big(_MIPD_ int len,const char *ptr,big x)
-{ /* convert len bytes into a big *
- * The first byte is the Most significant */
- int i,j,m,n,r;
- unsigned int dig;
- unsigned char ch;
- mr_small wrd;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
- MR_IN(140);
-
- zero(x);
-
- if (len<=0)
- {
- MR_OUT
- return;
- }
-/* remove leading zeros.. */
-
- while (*ptr==0)
- {
- ptr++; len--;
- if (len==0)
- {
- MR_OUT
- return;
- }
- }
-
-#ifndef MR_SIMPLE_BASE
- if (mr_mip->base==0)
- { /* pack bytes directly into big */
-#endif
-#ifndef MR_NOFULLWIDTH
- m=MIRACL/8;
- n=len/m;
-
- r=len%m;
- wrd=(mr_small)0;
- if (r!=0)
- {
- n++;
- for (j=0;jlen=n;
- if (n>mr_mip->nib && mr_mip->check)
- {
- mr_berror(_MIPP_ MR_ERR_OVERFLOW);
- MR_OUT
- return;
- }
- if (r!=0)
- {
- n--;
- x->w[n]=wrd;
- }
-
- for (i=n-1;i>=0;i--)
- {
- for (j=0;jw[i]=wrd;
- }
- mr_lzero(x); /* needed */
-#endif
-#ifndef MR_SIMPLE_BASE
- }
- else
- {
- for (i=0;iERNUM) break;
-#if MIRACL==8
- mr_shift(_MIPP_ x,1,x);
-#else
- premult(_MIPP_ x,256,x);
-#endif
- ch=MR_TOBYTE(ptr[i]);
- dig=ch;
- incr(_MIPP_ x,(int)dig,x);
- }
- }
-#endif
- MR_OUT
-}
-
-int big_to_bytes(_MIPD_ int max,big x,char *ptr,BOOL justify)
-{ /* convert positive big into octet string */
- int i,j,r,m,n,len,start;
- unsigned int dig;
- unsigned char ch;
- mr_small wrd;
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM || max<0) return 0;
-
- if (max==0 && justify) return 0;
- if (size(x)==0)
- {
- if (justify)
- {
- for (i=0;ibase==0)
- {
-#endif
-#ifndef MR_NOFULLWIDTH
- m=MIRACL/8;
- n=(int)(x->len&MR_OBITS);
- n--;
- len=n*m;
- wrd=x->w[n]; /* most significant */
- r=0;
- while (wrd!=(mr_small)0) { r++; wrd>>=8; len++;}
- r%=m;
-
- if (max>0 && len>max)
- {
- mr_berror(_MIPP_ MR_ERR_TOO_BIG);
- MR_OUT
- return 0;
- }
-
- if (justify)
- {
- start=max-len;
- for (i=0;iw[n--];
- for (i=r-1;i>=0;i--)
- {
- ptr[start+i]=(char)(wrd&0xFF);
- wrd>>=8;
- }
- }
-
- for (i=r;iw[n--];
- for (j=m-1;j>=0;j--)
- {
- ptr[start+i+j]=(char)(wrd&0xFF);
- wrd>>=8;
- }
- }
-#endif
-#ifndef MR_SIMPLE_BASE
- }
- else
- {
- copy(x,mr_mip->w1);
- for (len=0;;len++)
- {
- if (mr_mip->ERNUM) break;
-
- if (size(mr_mip->w1)==0)
- {
- if (justify)
- {
- if (len==max) break;
- }
- else break;
- }
-
- if (max>0 && len>=max)
- {
- mr_berror(_MIPP_ MR_ERR_TOO_BIG);
- MR_OUT
- return 0;
- }
-#if MIRACL==8
- ch=mr_mip->w1->w[0];
- mr_shift(_MIPP_ mr_mip->w1,-1,mr_mip->w1);
-#else
- dig=(unsigned int)subdiv(_MIPP_ mr_mip->w1,256,mr_mip->w1);
- ch=MR_TOBYTE(dig);
-#endif
- for (i=len;i>0;i--) ptr[i]=ptr[i-1];
- ptr[0]=MR_TOBYTE(ch);
- }
- }
-#endif
- MR_OUT
- if (justify) return max;
- else return len;
-}
-
-#ifndef MR_NO_ECC_MULTIADD
-
-/* Solinas's Joint Sparse Form */
-
-void mr_jsf(_MIPD_ big k0,big k1,big u0p,big u0m,big u1p,big u1m)
-{
- int j,u0,u1,d0,d1,l0,l1;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(191)
-
- d0=d1=0;
-
- convert(_MIPP_ 1,mr_mip->w1);
- copy(k0,mr_mip->w2);
- copy(k1,mr_mip->w3);
- zero(u0p); zero(u0m); zero(u1p); zero(u1m);
-
- j=0;
- while (!mr_mip->ERNUM)
- {
- if (size(mr_mip->w2)==0 && d0==0 && size(mr_mip->w3)==0 && d1==0) break;
- l0=remain(_MIPP_ mr_mip->w2,8);
- l0=(l0+d0)&0x7;
- l1=remain(_MIPP_ mr_mip->w3,8);
- l1=(l1+d1)&0x7;
-
- if (l0%2==0) u0=0;
- else
- {
- u0=2-(l0%4);
- if ((l0==3 || l0==5) && l1%4==2) u0=-u0;
- }
- if (l1%2==0) u1=0;
- else
- {
- u1=2-(l1%4);
- if ((l1==3 || l1==5) && l0%4==2) u1=-u1;
- }
-#ifndef MR_ALWAYS_BINARY
- if (mr_mip->base==mr_mip->base2)
- {
-#endif
- if (u0>0) mr_addbit(_MIPP_ u0p,j);
- if (u0<0) mr_addbit(_MIPP_ u0m,j);
- if (u1>0) mr_addbit(_MIPP_ u1p,j);
- if (u1<0) mr_addbit(_MIPP_ u1m,j);
-
-#ifndef MR_ALWAYS_BINARY
- }
- else
- {
- if (u0>0) add(_MIPP_ u0p,mr_mip->w1,u0p);
- if (u0<0) add(_MIPP_ u0m,mr_mip->w1,u0m);
- if (u1>0) add(_MIPP_ u1p,mr_mip->w1,u1p);
- if (u1<0) add(_MIPP_ u1m,mr_mip->w1,u1m);
- }
-#endif
-
- if (d0+d0==1+u0) d0=1-d0;
- if (d1+d1==1+u1) d1=1-d1;
-
- subdiv(_MIPP_ mr_mip->w2,2,mr_mip->w2);
- subdiv(_MIPP_ mr_mip->w3,2,mr_mip->w3);
-
-#ifndef MR_ALWAYS_BINARY
- if (mr_mip->base==mr_mip->base2)
-#endif
- j++;
-#ifndef MR_ALWAYS_BINARY
- else
- premult(_MIPP_ mr_mip->w1,2,mr_mip->w1);
-#endif
- }
- MR_OUT
- return;
-}
-
-#endif
diff --git a/crypto/sm2/miracl/mrarth2.c b/crypto/sm2/miracl/mrarth2.c
deleted file mode 100644
index 6daed161..00000000
--- a/crypto/sm2/miracl/mrarth2.c
+++ /dev/null
@@ -1,1584 +0,0 @@
-
-/***************************************************************************
- *
-Copyright 2013 CertiVox IOM Ltd. *
- *
-This file is part of CertiVox MIRACL Crypto SDK. *
- *
-The CertiVox MIRACL Crypto SDK provides developers with an *
-extensive and efficient set of cryptographic functions. *
-For further information about its features and functionalities please *
-refer to http://www.certivox.com *
- *
-* The CertiVox MIRACL Crypto SDK is free software: you can *
- redistribute it and/or modify it under the terms of the *
- GNU Affero General Public License as published by the *
- Free Software Foundation, either version 3 of the License, *
- or (at your option) any later version. *
- *
-* The CertiVox MIRACL Crypto SDK is distributed in the hope *
- that it will be useful, but WITHOUT ANY WARRANTY; without even the *
- implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. *
- See the GNU Affero General Public License for more details. *
- *
-* You should have received a copy of the GNU Affero General Public *
- License along with CertiVox MIRACL Crypto SDK. *
- If not, see . *
- *
-You can be released from the requirements of the license by purchasing *
-a commercial license. Buying such a license is mandatory as soon as you *
-develop commercial activities involving the CertiVox MIRACL Crypto SDK *
-without disclosing the source code of your own applications, or shipping *
-the CertiVox MIRACL Crypto SDK with a closed source product. *
- *
-***************************************************************************/
-/*
- * MIRACL arithmetic routines 2 - multiplying and dividing BIG NUMBERS.
- * mrarth2.c
- *
- */
-
-#include
-
-#ifdef MR_FP
-#include
-#endif
-
-#ifdef MR_WIN64
-#include
-#endif
-
-
-/* If a number has more than this number of digits, then squaring is faster */
-
-#define SQR_FASTER_THRESHOLD 5
-
-mr_small normalise(_MIPD_ big x,big y)
-{ /* normalise divisor */
- mr_small norm,r;
-#ifdef MR_FP
- mr_small dres;
-#endif
- int len;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- MR_IN(4)
-
- if (x!=y) copy(x,y);
- len=(int)(y->len&MR_OBITS);
-#ifndef MR_SIMPLE_BASE
- if (mr_mip->base==0)
- {
-#endif
-#ifndef MR_NOFULLWIDTH
- if ((r=y->w[len-1]+1)==0) norm=1;
-#ifdef MR_NOASM
- else norm=(mr_small)(((mr_large)1 << MIRACL)/r);
-#else
- else norm=muldvm((mr_small)1,(mr_small)0,r,&r);
-#endif
- if (norm!=1) mr_pmul(_MIPP_ y,norm,y);
-#endif
-#ifndef MR_SIMPLE_BASE
- }
- else
- {
- norm=MR_DIV(mr_mip->base,(mr_small)(y->w[len-1]+1));
- if (norm!=1) mr_pmul(_MIPP_ y,norm,y);
- }
-#endif
- MR_OUT
- return norm;
-}
-
-void multiply(_MIPD_ big x,big y,big z)
-{ /* multiply two big numbers: z=x.y */
- int i,xl,yl,j,ti;
- mr_small carry,*xg,*yg,*w0g;
-
-#ifdef MR_ITANIUM
- mr_small tm;
-#endif
-#ifdef MR_WIN64
- mr_small tm,tr;
-#endif
- mr_lentype sz;
- big w0;
-#ifdef MR_NOASM
- union doubleword dble;
- mr_large dbled;
- mr_large ldres;
-#endif
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
- if (y->len==0 || x->len==0)
- {
- zero(z);
- return;
- }
- if (x!=mr_mip->w5 && y!=mr_mip->w5 && z==mr_mip->w5) w0=mr_mip->w5;
- else w0=mr_mip->w0; /* local pointer */
-
- MR_IN(5)
-
-#ifdef MR_FLASH
- if (mr_notint(x) || mr_notint(y))
- {
- mr_berror(_MIPP_ MR_ERR_INT_OP);
- MR_OUT
- return;
- }
-#endif
- sz=((x->len&MR_MSBIT)^(y->len&MR_MSBIT));
- xl=(int)(x->len&MR_OBITS);
- yl=(int)(y->len&MR_OBITS);
- zero(w0);
- if (mr_mip->check && xl+yl>mr_mip->nib)
- {
- mr_berror(_MIPP_ MR_ERR_OVERFLOW);
- MR_OUT
- return;
- }
-#ifndef MR_SIMPLE_BASE
- if (mr_mip->base==0)
- {
-#endif
-#ifndef MR_NOFULLWIDTH
- xg=x->w; yg=y->w; w0g=w0->w;
- if (x==y && xl>SQR_FASTER_THRESHOLD)
- /* extra hassle make it not */
- /* worth it for small numbers */
- { /* fast squaring */
- for (i=0;iw[i]*x->w[j]+carry+w0->w[i+j];
- w0->w[i+j]=dble.h[MR_BOT];
- carry=dble.h[MR_TOP];
-#else
- muldvd2(x->w[i],x->w[j],&carry,&w0->w[i+j]);
-#endif
- }
- w0->w[xl+i]=carry;
-#endif
- }
-#ifdef INLINE_ASM
-#if INLINE_ASM == 1
- ASM mov cx,xl
- ASM shl cx,1
-#ifdef MR_LMM
- ASM push ds
- ASM push es
- ASM les bx,DWORD PTR w0g
-#else
- ASM mov bx,w0g
-#endif
- tcl5:
-#ifdef MR_LMM
- ASM rcl WORD PTR es:[bx],1
-#else
- ASM rcl WORD PTR [bx],1
-#endif
- ASM inc bx
- ASM inc bx
- ASM loop tcl5
-
- ASM cld
- ASM mov cx,xl
-#ifdef MR_LMM
- ASM les di,DWORD PTR w0g
- ASM lds si,DWORD PTR xg
-#else
- ASM mov di,w0g
- ASM mov si,xg
-#endif
-
- ASM xor bx,bx
- tcl7:
- ASM lodsw
- ASM mul ax
- ASM add ax,bx
- ASM adc dx,0
-#ifdef MR_LMM
- ASM add es:[di],ax
-#else
- ASM add [di],ax
-#endif
- ASM adc dx,0
- ASM xor bx,bx
- ASM inc di
- ASM inc di
-#ifdef MR_LMM
- ASM add es:[di],dx
-#else
- ASM add [di],dx
-#endif
- ASM adc bx,0
- ASM inc di
- ASM inc di
- ASM loop tcl7
-#ifdef MR_LMM
- ASM pop es
- ASM pop ds
-#endif
-#endif
-#if INLINE_ASM == 2
- ASM mov cx,xl
- ASM shl cx,1
-#ifdef MR_LMM
- ASM push ds
- ASM push es
- ASM les bx,DWORD PTR w0g
-#else
- ASM mov bx,w0g
-#endif
- tcl5:
-#ifdef MR_LMM
- ASM rcl DWORD PTR es:[bx],1
-#else
- ASM rcl DWORD PTR [bx],1
-#endif
- ASM inc bx
- ASM inc bx
- ASM inc bx
- ASM inc bx
- ASM loop tcl5
-
- ASM cld
- ASM mov cx,xl
-#ifdef MR_LMM
- ASM les di,DWORD PTR w0g
- ASM lds si,DWORD PTR xg
-#else
- ASM mov di,w0g
- ASM mov si,xg
-#endif
- ASM xor ebx,ebx
- tcl7:
- ASM lodsd
- ASM mul eax
- ASM add eax,ebx
- ASM adc edx,0
-#ifdef MR_LMM
- ASM add es:[di],eax
-#else
- ASM add [di],eax
-#endif
- ASM adc edx,0
- ASM xor ebx,ebx
- ASM add di,4
-#ifdef MR_LMM
- ASM add es:[di],edx
-#else
- ASM add [di],edx
-#endif
- ASM adc ebx,0
- ASM add di,4
- ASM loop tcl7
-#ifdef MR_LMM
- ASM pop es
- ASM pop ds
-#endif
-#endif
-#if INLINE_ASM == 3
- ASM mov ecx,xl
- ASM shl ecx,1
- ASM mov edi,w0g
- tcl5:
- ASM rcl DWORD PTR [edi],1
- ASM inc edi
- ASM inc edi
- ASM inc edi
- ASM inc edi
- ASM loop tcl5
-
- ASM mov ecx,xl
- ASM mov esi,xg
- ASM mov edi,w0g
- ASM xor ebx,ebx
- tcl7:
- ASM mov eax,[esi]
- ASM add esi,4
- ASM mul eax
- ASM add eax,ebx
- ASM adc edx,0
- ASM add [edi],eax
- ASM adc edx,0
- ASM xor ebx,ebx
- ASM add edi,4
- ASM add [edi],edx
- ASM adc ebx,0
- ASM add edi,4
- ASM dec ecx
- ASM jnz tcl7
-#endif
-#if INLINE_ASM == 4
- ASM (
- "movl %0,%%ecx\n"
- "shll $1,%%ecx\n"
- "movl %1,%%edi\n"
- "tcl5:\n"
- "rcll $1,(%%edi)\n"
- "incl %%edi\n"
- "incl %%edi\n"
- "incl %%edi\n"
- "incl %%edi\n"
- "loop tcl5\n"
-
- "movl %0,%%ecx\n"
- "movl %2,%%esi\n"
- "movl %1,%%edi\n"
- "xorl %%ebx,%%ebx\n"
- "tcl7:\n"
- "movl (%%esi),%%eax\n"
- "addl $4,%%esi\n"
- "mull %%eax\n"
- "addl %%ebx,%%eax\n"
- "adcl $0,%%edx\n"
- "addl %%eax,(%%edi)\n"
- "adcl $0,%%edx\n"
- "xorl %%ebx,%%ebx\n"
- "addl $4,%%edi\n"
- "addl %%edx,(%%edi)\n"
- "adcl $0,%%ebx\n"
- "addl $4,%%edi\n"
- "decl %%ecx\n"
- "jnz tcl7\n"
- :
- :"m"(xl),"m"(w0g),"m"(xg)
- :"eax","edi","esi","ebx","ecx","edx","memory"
- );
-#endif
-#endif
-#ifndef INLINE_ASM
- w0->len=xl+xl-1;
- mr_padd(_MIPP_ w0,w0,w0); /* double it */
- carry=0;
- for (i=0;iw[i]*x->w[i]+carry+w0->w[ti];
- w0->w[ti]=dble.h[MR_BOT];
- carry=dble.h[MR_TOP];
-#else
- muldvd2(x->w[i],x->w[i],&carry,&w0->w[ti]);
-#endif
- w0->w[ti+1]+=carry;
- if (w0->w[ti+1]w[i]*y->w[j]+carry+w0->w[i+j];
- w0->w[i+j]=dble.h[MR_BOT];
- carry=dble.h[MR_TOP];
-#else
- muldvd2(x->w[i],y->w[j],&carry,&w0->w[i+j]);
-#endif
- }
- w0->w[yl+i]=carry;
-#endif
- }
-#endif
-#ifndef MR_SIMPLE_BASE
- }
- else
- {
- if (x==y && xl>SQR_FASTER_THRESHOLD)
- { /* squaring can be done nearly twice as fast */
- for (i=0;iw[i]*x->w[j]+w0->w[i+j]+carry;
- #ifdef MR_FP_ROUNDING
- carry=(mr_small)MR_LROUND(dbled*mr_mip->inverse_base);
- #else
- #ifndef MR_FP
- if (mr_mip->base==mr_mip->base2)
- carry=(mr_small)(dbled>>mr_mip->lg2b);
- else
- #endif
- carry=(mr_small)MR_LROUND(dbled/mr_mip->base);
- #endif
- w0->w[i+j]=(mr_small)(dbled-(mr_large)carry*mr_mip->base);
-#else
-
- #ifdef MR_FP_ROUNDING
- carry=imuldiv(x->w[i],x->w[j],w0->w[i+j]+carry,mr_mip->base,mr_mip->inverse_base,&w0->w[i+j]);
- #else
- carry=muldiv(x->w[i],x->w[j],w0->w[i+j]+carry,mr_mip->base,&w0->w[i+j]);
- #endif
-#endif
- }
- w0->w[xl+i]=carry;
- }
- w0->len=xl+xl-1;
- mr_padd(_MIPP_ w0,w0,w0); /* double it */
- carry=0;
- for (i=0;iw[i]*x->w[i]+w0->w[ti]+carry;
-#ifdef MR_FP_ROUNDING
- carry=(mr_small)MR_LROUND(dbled*mr_mip->inverse_base);
-#else
-#ifndef MR_FP
- if (mr_mip->base==mr_mip->base2)
- carry=(mr_small)(dbled>>mr_mip->lg2b);
- else
-#endif
- carry=(mr_small)MR_LROUND(dbled/mr_mip->base);
-#endif
- w0->w[ti]=(mr_small)(dbled-(mr_large)carry*mr_mip->base);
-#else
-
-#ifdef MR_FP_ROUNDING
- carry=imuldiv(x->w[i],x->w[i],w0->w[ti]+carry,mr_mip->base,mr_mip->inverse_base,&w0->w[ti]);
-#else
- carry=muldiv(x->w[i],x->w[i],w0->w[ti]+carry,mr_mip->base,&w0->w[ti]);
-#endif
-
-#endif
- w0->w[ti+1]+=carry;
- carry=0;
- if (w0->w[ti+1]>=mr_mip->base)
- {
- carry=1;
- w0->w[ti+1]-=mr_mip->base;
- }
- }
- }
- else for (i=0;iw[i]*y->w[j]+w0->w[i+j]+carry;
-
-#ifdef MR_FP_ROUNDING
- carry=(mr_small)MR_LROUND(dbled*mr_mip->inverse_base);
-#else
-#ifndef MR_FP
- if (mr_mip->base==mr_mip->base2)
- carry=(mr_small)(dbled>>mr_mip->lg2b);
- else
-#endif
- carry=(mr_small)MR_LROUND(dbled/mr_mip->base);
-#endif
- w0->w[i+j]=(mr_small)(dbled-(mr_large)carry*mr_mip->base);
-#else
-
-#ifdef MR_FP_ROUNDING
- carry=imuldiv(x->w[i],y->w[j],w0->w[i+j]+carry,mr_mip->base,mr_mip->inverse_base,&w0->w[i+j]);
-#else
- carry=muldiv(x->w[i],y->w[j],w0->w[i+j]+carry,mr_mip->base,&w0->w[i+j]);
-#endif
-
-#endif
- }
- w0->w[yl+i]=carry;
- }
- }
-#endif
- w0->len=(sz|(xl+yl)); /* set length and sign of result */
-
- mr_lzero(w0);
- copy(w0,z);
- MR_OUT
-}
-
-void divide(_MIPD_ big x,big y,big z)
-{ /* divide two big numbers z=x/y : x=x mod y *
- * returns quotient only if divide(x,y,x) *
- * returns remainder only if divide(x,y,y) */
- mr_small carry,attemp,ldy,sdy,ra,r,d,tst,psum;
-#ifdef MR_FP
- mr_small dres;
-#endif
- mr_lentype sx,sy,sz;
- mr_small borrow,dig,*w0g,*yg;
- int i,k,m,x0,y0,w00;
- big w0;
-
-#ifdef MR_ITANIUM
- mr_small tm;
-#endif
-#ifdef MR_WIN64
- mr_small tm;
-#endif
-#ifdef MR_NOASM
- union doubleword dble;
- mr_large dbled;
- mr_large ldres;
-#endif
- BOOL check;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
- w0=mr_mip->w0;
-
- MR_IN(6)
-
- if (x==y) mr_berror(_MIPP_ MR_ERR_BAD_PARAMETERS);
-#ifdef MR_FLASH
- if (mr_notint(x) || mr_notint(y)) mr_berror(_MIPP_ MR_ERR_INT_OP);
-#endif
- if (y->len==0) mr_berror(_MIPP_ MR_ERR_DIV_BY_ZERO);
- if (mr_mip->ERNUM)
- {
- MR_OUT
- return;
- }
- sx=(x->len&MR_MSBIT); /* extract signs ... */
- sy=(y->len&MR_MSBIT);
- sz=(sx^sy);
- x->len&=MR_OBITS; /* ... and force operands to positive */
- y->len&=MR_OBITS;
- x0=(int)x->len;
- y0=(int)y->len;
- copy(x,w0);
- w00=(int)w0->len;
- if (mr_mip->check && (w00-y0+1>mr_mip->nib))
- {
- mr_berror(_MIPP_ MR_ERR_OVERFLOW);
- MR_OUT
- return;
- }
- d=0;
- if (x0==y0)
- {
- if (x0==1) /* special case - x and y are both mr_smalls */
- {
- d=MR_DIV(w0->w[0],y->w[0]);
- w0->w[0]=MR_REMAIN(w0->w[0],y->w[0]);
- mr_lzero(w0);
- }
- else if (MR_DIV(w0->w[x0-1],4)w[x0-1])
- while (mr_compare(w0,y)>=0)
- { /* mr_small quotient - so do up to four subtracts instead */
- mr_psub(_MIPP_ w0,y,w0);
- d++;
- }
- }
- if (mr_compare(w0,y)<0)
- { /* x less than y - so x becomes remainder */
- if (x!=z) /* testing parameters */
- {
- copy(w0,x);
- if (x->len!=0) x->len|=sx;
- }
- if (y!=z)
- {
- zero(z);
- z->w[0]=d;
- if (d>0) z->len=(sz|1);
- }
- y->len|=sy;
- MR_OUT
- return;
- }
-
- if (y0==1)
- { /* y is int - so use subdiv instead */
-#ifdef MR_FP_ROUNDING
- r=mr_sdiv(_MIPP_ w0,y->w[0],mr_invert(y->w[0]),w0);
-#else
- r=mr_sdiv(_MIPP_ w0,y->w[0],w0);
-#endif
- if (y!=z)
- {
- copy(w0,z);
- z->len|=sz;
- }
- if (x!=z)
- {
- zero(x);
- x->w[0]=r;
- if (r>0) x->len=(sx|1);
- }
- y->len|=sy;
- MR_OUT
- return;
- }
- if (y!=z) zero(z);
- d=normalise(_MIPP_ y,y);
- check=mr_mip->check;
- mr_mip->check=OFF;
-#ifndef MR_SIMPLE_BASE
- if (mr_mip->base==0)
- {
-#endif
-#ifndef MR_NOFULLWIDTH
- if (d!=1) mr_pmul(_MIPP_ w0,d,w0);
- ldy=y->w[y0-1];
- sdy=y->w[y0-2];
- w0g=w0->w; yg=y->w;
- for (k=w00-1;k>=y0-1;k--)
- { /* long division */
-#ifdef INLINE_ASM
-#if INLINE_ASM == 1
-#ifdef MR_LMM
- ASM push ds
- ASM lds bx,DWORD PTR w0g
-#else
- ASM mov bx,w0g
-#endif
- ASM mov si,k
- ASM shl si,1
- ASM add bx,si
- ASM mov dx,[bx+2]
- ASM mov ax,[bx]
- ASM cmp dx,ldy
- ASM jne tcl8
- ASM mov di,0xffff
- ASM mov si,ax
- ASM add si,ldy
- ASM jc tcl12
- ASM jmp tcl10
- tcl8:
- ASM div WORD PTR ldy
- ASM mov di,ax
- ASM mov si,dx
- tcl10:
- ASM mov ax,sdy
- ASM mul di
- ASM cmp dx,si
- ASM jb tcl12
- ASM jne tcl11
- ASM cmp ax,[bx-2]
- ASM jbe tcl12
- tcl11:
- ASM dec di
- ASM add si,ldy
- ASM jnc tcl10
- tcl12:
- ASM mov attemp,di
-#ifdef MR_LMM
- ASM pop ds
-#endif
-#endif
-/* NOTE push and pop of esi/edi should not be necessary - Borland C bug *
- * These pushes are needed here even if register variables are disabled */
-#if INLINE_ASM == 2
- ASM push esi
- ASM push edi
-#ifdef MR_LMM
- ASM push ds
- ASM lds bx,DWORD PTR w0g
-#else
- ASM mov bx,w0g
-#endif
- ASM mov si,k
- ASM shl si,2
- ASM add bx,si
- ASM mov edx,[bx+4]
- ASM mov eax,[bx]
- ASM cmp edx,ldy
- ASM jne tcl8
- ASM mov edi,0xffffffff
- ASM mov esi,eax
- ASM add esi,ldy
- ASM jc tcl12
- ASM jmp tcl10
- tcl8:
- ASM div DWORD PTR ldy
- ASM mov edi,eax
- ASM mov esi,edx
- tcl10:
- ASM mov eax,sdy
- ASM mul edi
- ASM cmp edx,esi
- ASM jb tcl12
- ASM jne tcl11
- ASM cmp eax,[bx-4]
- ASM jbe tcl12
- tcl11:
- ASM dec edi
- ASM add esi,ldy
- ASM jnc tcl10
- tcl12:
- ASM mov attemp,edi
-#ifdef MR_LMM
- ASM pop ds
-#endif
- ASM pop edi
- ASM pop esi
-#endif
-#if INLINE_ASM == 3
- ASM push esi
- ASM push edi
- ASM mov ebx,w0g
- ASM mov esi,k
- ASM shl esi,2
- ASM add ebx,esi
- ASM mov edx,[ebx+4]
- ASM mov eax,[ebx]
- ASM cmp edx,ldy
- ASM jne tcl8
- ASM mov edi,0xffffffff
- ASM mov esi,eax
- ASM add esi,ldy
- ASM jc tcl12
- ASM jmp tcl10
- tcl8:
- ASM div DWORD PTR ldy
- ASM mov edi,eax
- ASM mov esi,edx
- tcl10:
- ASM mov eax,sdy
- ASM mul edi
- ASM cmp edx,esi
- ASM jb tcl12
- ASM jne tcl11
- ASM cmp eax,[ebx-4]
- ASM jbe tcl12
- tcl11:
- ASM dec edi
- ASM add esi,ldy
- ASM jnc tcl10
- tcl12:
- ASM mov attemp,edi
- ASM pop edi
- ASM pop esi
-#endif
-#if INLINE_ASM == 4
- ASM (
- "movl %1,%%ebx\n"
- "movl %2,%%esi\n"
- "shll $2,%%esi\n"
- "addl %%esi,%%ebx\n"
- "movl 4(%%ebx),%%edx\n"
- "movl (%%ebx),%%eax\n"
- "cmpl %3,%%edx\n"
- "jne tcl8\n"
- "movl $0xffffffff,%%edi\n"
- "movl %%eax,%%esi\n"
- "addl %3,%%esi\n"
- "jc tcl12\n"
- "jmp tcl10\n"
- "tcl8:\n"
- "divl %3\n"
- "movl %%eax,%%edi\n"
- "movl %%edx,%%esi\n"
- "tcl10:\n"
- "movl %4,%%eax\n"
- "mull %%edi\n"
- "cmpl %%esi,%%edx\n"
- "jb tcl12\n"
- "jne tcl11\n"
- "cmpl -4(%%ebx),%%eax\n"
- "jbe tcl12\n"
- "tcl11:\n"
- "decl %%edi\n"
- "addl %3,%%esi\n"
- "jnc tcl10\n"
- "tcl12:\n"
- "movl %%edi,%0\n"
- :"=m"(attemp)
- :"m"(w0g),"m"(k),"m"(ldy),"m"(sdy)
- :"eax","edi","esi","ebx","ecx","edx","memory"
- );
-#endif
-#endif
-#ifndef INLINE_ASM
- carry=0;
- if (w0->w[k+1]==ldy) /* guess next quotient digit */
- {
- attemp=(mr_small)(-1);
- ra=ldy+w0->w[k];
- if (raw[k];
- dble.h[MR_TOP]=w0->w[k+1];
- attemp=(mr_small)(dble.d/ldy);
- ra=(mr_small)(dble.d-(mr_large)attemp*ldy);
- }
-#else
- else attemp=muldvm(w0->w[k+1],w0->w[k],ldy,&ra);
-#endif
- while (carry==0)
- {
-#ifdef MR_NOASM
- dble.d=(mr_large)attemp*sdy;
- r=dble.h[MR_BOT];
- tst=dble.h[MR_TOP];
-#else
- tst=muldvd(sdy,attemp,(mr_small)0,&r);
-#endif
- if (tst< ra || (tst==ra && r<=w0->w[k-1])) break;
- attemp--; /* refine guess */
- ra+=ldy;
- if (ra0)
- { /* do partial subtraction */
- borrow=0;
- /* inline - substitutes for loop below */
-#ifdef INLINE_ASM
-#if INLINE_ASM == 1
- ASM cld
- ASM mov cx,y0
- ASM mov si,m
- ASM shl si,1
- ASM mov di,attemp
-#ifdef MR_LMM
- ASM push ds
- ASM push es
- ASM les bx,DWORD PTR w0g
- ASM add bx,si
- ASM sub bx,2
- ASM lds si,DWORD PTR yg
-#else
- ASM mov bx,w0g
- ASM add bx,si
- ASM sub bx,2
- ASM mov si,yg
-#endif
- ASM push bp
- ASM xor bp,bp
-
- tcl3:
- ASM lodsw
- ASM mul di
- ASM add ax,bp
- ASM adc dx,0
- ASM inc bx
- ASM inc bx
-#ifdef MR_LMM
- ASM sub es:[bx],ax
-#else
- ASM sub [bx],ax
-#endif
- ASM adc dx,0
- ASM mov bp,dx
- ASM loop tcl3
-
- ASM mov ax,bp
- ASM pop bp
-#ifdef MR_LMM
- ASM pop es
- ASM pop ds
-#endif
- ASM mov borrow,ax
-#endif
-/* NOTE push and pop of esi/edi should not be necessary - Borland C bug *
- * These pushes are needed here even if register variables are disabled */
-#if INLINE_ASM == 2
- ASM push esi
- ASM push edi
- ASM cld
- ASM mov cx,y0
- ASM mov si,m
- ASM shl si,2
- ASM mov edi,attemp
-#ifdef MR_LMM
- ASM push ds
- ASM push es
- ASM les bx,DWORD PTR w0g
- ASM add bx,si
- ASM sub bx,4
- ASM lds si,DWORD PTR yg
-#else
- ASM mov bx,w0g
- ASM add bx,si
- ASM sub bx,4
- ASM mov si,yg
-#endif
- ASM push ebp
- ASM xor ebp,ebp
-
- tcl3:
- ASM lodsd
- ASM mul edi
- ASM add eax,ebp
- ASM adc edx,0
- ASM add bx,4
-#ifdef MR_LMM
- ASM sub es:[bx],eax
-#else
- ASM sub [bx],eax
-#endif
- ASM adc edx,0
- ASM mov ebp,edx
- ASM loop tcl3
-
- ASM mov eax,ebp
- ASM pop ebp
-#ifdef MR_LMM
- ASM pop es
- ASM pop ds
-#endif
- ASM mov borrow,eax
- ASM pop edi
- ASM pop esi
-#endif
-#if INLINE_ASM == 3
- ASM push esi
- ASM push edi
- ASM mov ecx,y0
- ASM mov esi,m
- ASM shl esi,2
- ASM mov edi,attemp
- ASM mov ebx,w0g
- ASM add ebx,esi
- ASM mov esi,yg
- ASM sub ebx,esi
- ASM sub ebx,4
- ASM push ebp
- ASM xor ebp,ebp
-
- tcl3:
- ASM mov eax,[esi]
- ASM add esi,4
- ASM mul edi
- ASM add eax,ebp
- ASM mov ebp,[esi+ebx]
- ASM adc edx,0
- ASM sub ebp,eax
- ASM adc edx,0
- ASM mov [esi+ebx],ebp
- ASM dec ecx
- ASM mov ebp,edx
- ASM jnz tcl3
-
- ASM mov eax,ebp
- ASM pop ebp
- ASM mov borrow,eax
- ASM pop edi
- ASM pop esi
-#endif
-#if INLINE_ASM == 4
- ASM (
- "movl %1,%%ecx\n"
- "movl %2,%%esi\n"
- "shll $2,%%esi\n"
- "movl %3,%%edi\n"
- "movl %4,%%ebx\n"
- "addl %%esi,%%ebx\n"
- "movl %5,%%esi\n"
- "subl %%esi,%%ebx\n"
- "subl $4,%%ebx\n"
- "pushl %%ebp\n"
- "xorl %%ebp,%%ebp\n"
- "tcl3:\n"
- "movl (%%esi),%%eax\n"
- "addl $4,%%esi\n"
- "mull %%edi\n"
- "addl %%ebp,%%eax\n"
- "movl (%%esi,%%ebx),%%ebp\n"
- "adcl $0,%%edx\n"
- "subl %%eax,%%ebp\n"
- "adcl $0,%%edx\n"
- "movl %%ebp,(%%esi,%%ebx)\n"
- "decl %%ecx\n"
- "movl %%edx,%%ebp\n"
- "jnz tcl3\n"
-
- "movl %%ebp,%%eax\n"
- "popl %%ebp\n"
- "movl %%eax,%0\n"
-
- :"=m"(borrow)
- :"m"(y0),"m"(m),"m"(attemp),"m"(w0g),"m"(yg)
- :"eax","edi","esi","ebx","ecx","edx","memory"
- );
-#endif
-#endif
-#ifndef INLINE_ASM
- for (i=0;iw[i]+borrow;
- dig=dble.h[MR_BOT];
- borrow=dble.h[MR_TOP];
-#else
- borrow=muldvd(attemp,y->w[i],borrow,&dig);
-#endif
- if (w0->w[m+i]w[m+i]-=dig;
- }
-#endif
-
- if (w0->w[k+1]w[k+1]=0;
- carry=0;
- for (i=0;iw[m+i]+y->w[i]+carry;
- if (psum>y->w[i]) carry=0;
- if (psumw[i]) carry=1;
- w0->w[m+i]=psum;
- }
- attemp--; /* ... and adjust guess */
- }
- else w0->w[k+1]-=borrow;
- }
- if (k==w00-1 && attemp==0) w00--;
- else if (y!=z) z->w[m]=attemp;
- }
-#endif
-#ifndef MR_SIMPLE_BASE
- }
- else
- { /* have to do it the hard way */
- if (d!=1) mr_pmul(_MIPP_ w0,d,w0);
- ldy=y->w[y0-1];
- sdy=y->w[y0-2];
-
- for (k=w00-1;k>=y0-1;k--)
- { /* long division */
-
-
- if (w0->w[k+1]==ldy) /* guess next quotient digit */
- {
- attemp=mr_mip->base-1;
- ra=ldy+w0->w[k];
- }
-#ifdef MR_NOASM
- else
- {
- dbled=(mr_large)w0->w[k+1]*mr_mip->base+w0->w[k];
- attemp=(mr_small)MR_LROUND(dbled/ldy);
- ra=(mr_small)(dbled-(mr_large)attemp*ldy);
- }
-#else
- else attemp=muldiv(w0->w[k+1],mr_mip->base,w0->w[k],ldy,&ra);
-#endif
- while (rabase)
- {
-#ifdef MR_NOASM
- dbled=(mr_large)sdy*attemp;
-#ifdef MR_FP_ROUNDING
- tst=(mr_small)MR_LROUND(dbled*mr_mip->inverse_base);
-#else
-#ifndef MR_FP
- if (mr_mip->base==mr_mip->base2)
- tst=(mr_small)(dbled>>mr_mip->lg2b);
- else
-#endif
- tst=(mr_small)MR_LROUND(dbled/mr_mip->base);
-#endif
- r=(mr_small)(dbled-(mr_large)tst*mr_mip->base);
-#else
-#ifdef MR_FP_ROUNDING
- tst=imuldiv(sdy,attemp,(mr_small)0,mr_mip->base,mr_mip->inverse_base,&r);
-#else
- tst=muldiv(sdy,attemp,(mr_small)0,mr_mip->base,&r);
-#endif
-#endif
- if (tst< ra || (tst==ra && r<=w0->w[k-1])) break;
- attemp--; /* refine guess */
- ra+=ldy;
- }
- m=k-y0+1;
- if (attemp>0)
- { /* do partial subtraction */
- borrow=0;
- for (i=0;iw[i]+borrow;
-#ifdef MR_FP_ROUNDING
- borrow=(mr_small)MR_LROUND(dbled*mr_mip->inverse_base);
-#else
-#ifndef MR_FP
- if (mr_mip->base==mr_mip->base2)
- borrow=(mr_small)(dbled>>mr_mip->lg2b);
- else
-#endif
- borrow=(mr_small)MR_LROUND(dbled/mr_mip->base);
-#endif
- dig=(mr_small)(dbled-(mr_large)borrow*mr_mip->base);
-#else
-#ifdef MR_FP_ROUNDING
- borrow=imuldiv(attemp,y->w[i],borrow,mr_mip->base,mr_mip->inverse_base,&dig);
-#else
- borrow=muldiv(attemp,y->w[i],borrow,mr_mip->base,&dig);
-#endif
-#endif
- if (w0->w[m+i]w[m+i]+=(mr_mip->base-dig);
- }
- else w0->w[m+i]-=dig;
- }
- if (w0->w[k+1]w[k+1]=0;
- carry=0;
- for (i=0;iw[m+i]+y->w[i]+carry;
- carry=0;
- if (psum>=mr_mip->base)
- {
- carry=1;
- psum-=mr_mip->base;
- }
- w0->w[m+i]=psum;
- }
- attemp--; /* ... and adjust guess */
- }
- else
- w0->w[k+1]-=borrow;
- }
- if (k==w00-1 && attemp==0) w00--;
- else if (y!=z) z->w[m]=attemp;
- }
- }
-#endif
- if (y!=z) z->len=((w00-y0+1)|sz); /* set sign and length of result */
-
- w0->len=y0;
-
- mr_lzero(y);
- mr_lzero(z);
-
- if (x!=z)
- {
- mr_lzero(w0);
-#ifdef MR_FP_ROUNDING
- if (d!=1) mr_sdiv(_MIPP_ w0,d,mr_invert(d),x);
-#else
- if (d!=1) mr_sdiv(_MIPP_ w0,d,x);
-#endif
- else copy(w0,x);
- if (x->len!=0) x->len|=sx;
- }
-#ifdef MR_FP_ROUNDING
- if (d!=1) mr_sdiv(_MIPP_ y,d,mr_invert(d),y);
-#else
- if (d!=1) mr_sdiv(_MIPP_ y,d,y);
-#endif
- y->len|=sy;
- mr_mip->check=check;
-
- MR_OUT
-}
-
-BOOL divisible(_MIPD_ big x,big y)
-{ /* returns y|x, that is TRUE if y divides x exactly */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return FALSE;
-
- MR_IN(87)
-
- copy (x,mr_mip->w0);
- divide(_MIPP_ mr_mip->w0,y,y);
-
- MR_OUT
- if (size(mr_mip->w0)==0) return TRUE;
- else return FALSE;
-}
-
-void mad(_MIPD_ big x,big y,big z,big w,big q,big r)
-{ /* Multiply, Add and Divide; q=(x*y+z)/w remainder r *
- * returns remainder only if w=q, quotient only if q=r *
- * add done only if x, y and z are distinct. */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- BOOL check;
- if (mr_mip->ERNUM) return;
-
- MR_IN(24)
- if (w==r)
- {
- mr_berror(_MIPP_ MR_ERR_BAD_PARAMETERS);
- MR_OUT
- return;
- }
- check=mr_mip->check;
- mr_mip->check=OFF; /* turn off some error checks */
-
- multiply(_MIPP_ x,y,mr_mip->w0);
- if (x!=z && y!=z) add(_MIPP_ mr_mip->w0,z,mr_mip->w0);
-
- divide(_MIPP_ mr_mip->w0,w,q);
- if (q!=r) copy(mr_mip->w0,r);
- mr_mip->check=check;
- MR_OUT
-}
-
diff --git a/crypto/sm2/miracl/mrarth3.c b/crypto/sm2/miracl/mrarth3.c
deleted file mode 100644
index 5f4deb74..00000000
--- a/crypto/sm2/miracl/mrarth3.c
+++ /dev/null
@@ -1,231 +0,0 @@
-
-/***************************************************************************
- *
-Copyright 2013 CertiVox IOM Ltd. *
- *
-This file is part of CertiVox MIRACL Crypto SDK. *
- *
-The CertiVox MIRACL Crypto SDK provides developers with an *
-extensive and efficient set of cryptographic functions. *
-For further information about its features and functionalities please *
-refer to http://www.certivox.com *
- *
-* The CertiVox MIRACL Crypto SDK is free software: you can *
- redistribute it and/or modify it under the terms of the *
- GNU Affero General Public License as published by the *
- Free Software Foundation, either version 3 of the License, *
- or (at your option) any later version. *
- *
-* The CertiVox MIRACL Crypto SDK is distributed in the hope *
- that it will be useful, but WITHOUT ANY WARRANTY; without even the *
- implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. *
- See the GNU Affero General Public License for more details. *
- *
-* You should have received a copy of the GNU Affero General Public *
- License along with CertiVox MIRACL Crypto SDK. *
- If not, see . *
- *
-You can be released from the requirements of the license by purchasing *
-a commercial license. Buying such a license is mandatory as soon as you *
-develop commercial activities involving the CertiVox MIRACL Crypto SDK *
-without disclosing the source code of your own applications, or shipping *
-the CertiVox MIRACL Crypto SDK with a closed source product. *
- *
-***************************************************************************/
-/*
- * MIRACL arithmetic routines 3 - simple powers and roots
- * mrarth3.c
- */
-
-#include
-#include
-
-void expint(_MIPD_ int b,int n,big x)
-{ /* sets x=b^n */
- unsigned int bit,un;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
- convert(_MIPP_ 1,x);
- if (n==0) return;
-
- MR_IN(50)
-
- if (n<0)
- {
- mr_berror(_MIPP_ MR_ERR_NEG_POWER);
- MR_OUT
- return;
- }
- if (b==2) expb2(_MIPP_ n,x);
- else
- {
- bit=1;
- un=(unsigned int)n;
- while (un>=bit) bit<<=1;
- bit>>=1;
- while (bit>0)
- { /* ltr method */
- multiply(_MIPP_ x,x,x);
- if ((bit&un)!=0) premult(_MIPP_ x,b,x);
- bit>>=1;
- }
- }
- MR_OUT
-}
-
-void power(_MIPD_ big x,long n,big z,big w)
-{ /* raise big number to int power w=x^n *
- * (mod z if z and w distinct) */
- mr_small norm;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- copy(x,mr_mip->w5);
- zero(w);
- if(mr_mip->ERNUM || size(mr_mip->w5)==0) return;
- convert(_MIPP_ 1,w);
- if (n==0L) return;
-
- MR_IN(17)
-
- if (n<0L)
- {
- mr_berror(_MIPP_ MR_ERR_NEG_POWER);
- MR_OUT
- return;
- }
-
- if (w==z) forever
- { /* "Russian peasant" exponentiation */
- if (n%2!=0L)
- multiply(_MIPP_ w,mr_mip->w5,w);
- n/=2L;
- if (mr_mip->ERNUM || n==0L) break;
- multiply(_MIPP_ mr_mip->w5,mr_mip->w5,mr_mip->w5);
- }
- else
- {
- norm=normalise(_MIPP_ z,z);
- divide(_MIPP_ mr_mip->w5,z,z);
- forever
- {
- if (mr_mip->user!=NULL) (*mr_mip->user)();
-
- if (n%2!=0L) mad(_MIPP_ w,mr_mip->w5,mr_mip->w5,z,z,w);
- n/=2L;
- if (mr_mip->ERNUM || n==0L) break;
- mad(_MIPP_ mr_mip->w5,mr_mip->w5,mr_mip->w5,z,z,mr_mip->w5);
- }
- if (norm!=1)
- {
-#ifdef MR_FP_ROUNDING
- mr_sdiv(_MIPP_ z,norm,mr_invert(norm),z);
-#else
- mr_sdiv(_MIPP_ z,norm,z);
-#endif
- divide(_MIPP_ w,z,z);
- }
- }
-
- MR_OUT
-}
-
-BOOL nroot(_MIPD_ big x,int n,big w)
-{ /* extract lower approximation to nth root *
- * w=x^(1/n) returns TRUE for exact root *
- * uses Newtons method */
- int sx,dif,s,p,d,lg2,lgx,rem;
- BOOL full;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return FALSE;
- if (size(x)==0 || n==1)
- {
- copy(x,w);
- return TRUE;
- }
-
- MR_IN(16)
-
- if (n<1) mr_berror(_MIPP_ MR_ERR_BAD_ROOT);
- sx=exsign(x);
- if (n%2==0 && sx==MINUS) mr_berror(_MIPP_ MR_ERR_NEG_ROOT);
- if (mr_mip->ERNUM)
- {
- MR_OUT
- return FALSE;
- }
- insign(PLUS,x);
- lgx=logb2(_MIPP_ x);
- if (n>=lgx)
- { /* root must be 1 */
- insign(sx,x);
- convert(_MIPP_ sx,w);
- MR_OUT
- if (lgx==1) return TRUE;
- else return FALSE;
- }
- expb2(_MIPP_ 1+(lgx-1)/n,mr_mip->w2); /* guess root as 2^(log2(x)/n) */
- s=(-(((int)x->len-1)/n)*n);
- mr_shift(_MIPP_ mr_mip->w2,s/n,mr_mip->w2);
- lg2=logb2(_MIPP_ mr_mip->w2)-1;
- full=FALSE;
- if (s==0) full=TRUE;
- d=0;
- p=1;
- while (!mr_mip->ERNUM)
- { /* Newtons method */
- copy(mr_mip->w2,mr_mip->w3);
- mr_shift(_MIPP_ x,s,mr_mip->w4);
- mr_mip->check=OFF;
- power(_MIPP_ mr_mip->w2,n-1,mr_mip->w6,mr_mip->w6);
- mr_mip->check=ON;
- divide(_MIPP_ mr_mip->w4,mr_mip->w6,mr_mip->w2);
- rem=size(mr_mip->w4);
- subtract(_MIPP_ mr_mip->w2,mr_mip->w3,mr_mip->w2);
- dif=size(mr_mip->w2);
- subdiv(_MIPP_ mr_mip->w2,n,mr_mip->w2);
- add(_MIPP_ mr_mip->w2,mr_mip->w3,mr_mip->w2);
- p*=2;
- if(plg2b) continue;
- if (full && mr_abs(dif)w2,1,mr_mip->w2);
- mr_mip->check=OFF;
- power(_MIPP_ mr_mip->w2,n,mr_mip->w6,mr_mip->w6);
- mr_mip->check=ON;
- dif=mr_compare(x,mr_mip->w6);
- }
- copy(mr_mip->w2,w);
- insign(sx,w);
- insign(sx,x);
- MR_OUT
- if (rem==0 && dif==0) return TRUE;
- else return FALSE;
- }
- else
- { /* adjust precision */
- d*=2;
- if (d==0) d=1;
- s+=d*n;
- if (s>=0)
- {
- d-=s/n;
- s=0;
- full=TRUE;
- }
- mr_shift(_MIPP_ mr_mip->w2,d,mr_mip->w2);
- }
- p/=2;
- }
- MR_OUT
- return FALSE;
-}
-
diff --git a/crypto/sm2/miracl/mrbits.c b/crypto/sm2/miracl/mrbits.c
deleted file mode 100644
index b14021f8..00000000
--- a/crypto/sm2/miracl/mrbits.c
+++ /dev/null
@@ -1,245 +0,0 @@
-
-/***************************************************************************
- *
-Copyright 2013 CertiVox IOM Ltd. *
- *
-This file is part of CertiVox MIRACL Crypto SDK. *
- *
-The CertiVox MIRACL Crypto SDK provides developers with an *
-extensive and efficient set of cryptographic functions. *
-For further information about its features and functionalities please *
-refer to http://www.certivox.com *
- *
-* The CertiVox MIRACL Crypto SDK is free software: you can *
- redistribute it and/or modify it under the terms of the *
- GNU Affero General Public License as published by the *
- Free Software Foundation, either version 3 of the License, *
- or (at your option) any later version. *
- *
-* The CertiVox MIRACL Crypto SDK is distributed in the hope *
- that it will be useful, but WITHOUT ANY WARRANTY; without even the *
- implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. *
- See the GNU Affero General Public License for more details. *
- *
-* You should have received a copy of the GNU Affero General Public *
- License along with CertiVox MIRACL Crypto SDK. *
- If not, see . *
- *
-You can be released from the requirements of the license by purchasing *
-a commercial license. Buying such a license is mandatory as soon as you *
-develop commercial activities involving the CertiVox MIRACL Crypto SDK *
-without disclosing the source code of your own applications, or shipping *
-the CertiVox MIRACL Crypto SDK with a closed source product. *
- *
-***************************************************************************/
-/*
- * MIRACL bit manipulation routines
- * mrbits.c
- */
-
-#include
-#include
-
-#ifdef MR_FP
-#include
-#endif
-
-int logb2(_MIPD_ big x)
-{ /* returns number of bits in x */
- int xl,lg2;
- mr_small top;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM || size(x)==0) return 0;
-
- MR_IN(49)
-
-
-#ifndef MR_ALWAYS_BINARY
- if (mr_mip->base==mr_mip->base2)
- {
-#endif
- xl=(int)(x->len&MR_OBITS);
- lg2=mr_mip->lg2b*(xl-1);
- top=x->w[xl-1];
- while (top>=1)
- {
- lg2++;
- top/=2;
- }
-
-#ifndef MR_ALWAYS_BINARY
- }
- else
- {
- copy(x,mr_mip->w0);
- insign(PLUS,mr_mip->w0);
- lg2=0;
- while (mr_mip->w0->len>1)
- {
-#ifdef MR_FP_ROUNDING
- mr_sdiv(_MIPP_ mr_mip->w0,mr_mip->base2,mr_invert(mr_mip->base2),mr_mip->w0);
-#else
- mr_sdiv(_MIPP_ mr_mip->w0,mr_mip->base2,mr_mip->w0);
-#endif
- lg2+=mr_mip->lg2b;
- }
-
- while (mr_mip->w0->w[0]>=1)
- {
- lg2++;
- mr_mip->w0->w[0]/=2;
- }
- }
-#endif
- MR_OUT
- return lg2;
-}
-
-void sftbit(_MIPD_ big x,int n,big z)
-{ /* shift x by n bits */
- int m;
- mr_small sm;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
- copy(x,z);
- if (n==0) return;
-
- MR_IN(47)
-
- m=mr_abs(n);
- sm=mr_shiftbits((mr_small)1,m%mr_mip->lg2b);
- if (n>0)
- { /* shift left */
-
-#ifndef MR_ALWAYS_BINARY
- if (mr_mip->base==mr_mip->base2)
- {
-#endif
- mr_shift(_MIPP_ z,n/mr_mip->lg2b,z);
- mr_pmul(_MIPP_ z,sm,z);
-#ifndef MR_ALWAYS_BINARY
- }
- else
- {
- expb2(_MIPP_ m,mr_mip->w1);
- multiply(_MIPP_ z,mr_mip->w1,z);
- }
-#endif
- }
- else
- { /* shift right */
-
-#ifndef MR_ALWAYS_BINARY
- if (mr_mip->base==mr_mip->base2)
- {
-#endif
- mr_shift(_MIPP_ z,n/mr_mip->lg2b,z);
-#ifdef MR_FP_ROUNDING
- mr_sdiv(_MIPP_ z,sm,mr_invert(sm),z);
-#else
- mr_sdiv(_MIPP_ z,sm,z);
-#endif
-
-#ifndef MR_ALWAYS_BINARY
- }
- else
- {
- expb2(_MIPP_ m,mr_mip->w1);
- divide(_MIPP_ z,mr_mip->w1,z);
- }
-#endif
- }
- MR_OUT
-}
-
-void expb2(_MIPD_ int n,big x)
-{ /* sets x=2^n */
- int r,p;
-#ifndef MR_ALWAYS_BINARY
- int i;
-#endif
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
- convert(_MIPP_ 1,x);
- if (n==0) return;
-
- MR_IN(149)
-
- if (n<0)
- {
- mr_berror(_MIPP_ MR_ERR_NEG_POWER);
- MR_OUT
- return;
- }
- r=n/mr_mip->lg2b;
- p=n%mr_mip->lg2b;
-
-#ifndef MR_ALWAYS_BINARY
- if (mr_mip->base==mr_mip->base2)
- {
-#endif
- mr_shift(_MIPP_ x,r,x);
- x->w[x->len-1]=mr_shiftbits(x->w[x->len-1],p);
-#ifndef MR_ALWAYS_BINARY
- }
- else
- {
- for (i=1;i<=r;i++)
- mr_pmul(_MIPP_ x,mr_mip->base2,x);
- mr_pmul(_MIPP_ x,mr_shiftbits((mr_small)1,p),x);
- }
-#endif
- MR_OUT
-}
-
-#ifndef MR_NO_RAND
-
-void bigbits(_MIPD_ int n,big x)
-{ /* sets x as random < 2^n */
- mr_small r;
- mr_lentype wlen;
-#ifdef MR_FP
- mr_small dres;
-#endif
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- zero(x);
- if (mr_mip->ERNUM || n<=0) return;
-
- MR_IN(150)
-
- expb2(_MIPP_ n,mr_mip->w1);
- wlen=mr_mip->w1->len;
- do
- {
- r=brand(_MIPPO_ );
- if (mr_mip->base==0) x->w[x->len++]=r;
- else x->w[x->len++]=MR_REMAIN(r,mr_mip->base);
- } while (x->lenbase==mr_mip->base2)
- {
-#endif
-
- x->w[wlen-1]=MR_REMAIN(x->w[wlen-1],mr_mip->w1->w[wlen-1]);
- mr_lzero(x);
-
-#ifndef MR_ALWAYS_BINARY
- }
- else
- {
- divide(_MIPP_ x,mr_mip->w1,mr_mip->w1);
- }
-#endif
-
- MR_OUT
-}
-
-#endif
diff --git a/crypto/sm2/miracl/mrcore.c b/crypto/sm2/miracl/mrcore.c
deleted file mode 100644
index 855b063f..00000000
--- a/crypto/sm2/miracl/mrcore.c
+++ /dev/null
@@ -1,2290 +0,0 @@
-
-/***************************************************************************
- *
-Copyright 2013 CertiVox IOM Ltd. *
- *
-This file is part of CertiVox MIRACL Crypto SDK. *
- *
-The CertiVox MIRACL Crypto SDK provides developers with an *
-extensive and efficient set of cryptographic functions. *
-For further information about its features and functionalities please *
-refer to http://www.certivox.com *
- *
-* The CertiVox MIRACL Crypto SDK is free software: you can *
- redistribute it and/or modify it under the terms of the *
- GNU Affero General Public License as published by the *
- Free Software Foundation, either version 3 of the License, *
- or (at your option) any later version. *
- *
-* The CertiVox MIRACL Crypto SDK is distributed in the hope *
- that it will be useful, but WITHOUT ANY WARRANTY; without even the *
- implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. *
- See the GNU Affero General Public License for more details. *
- *
-* You should have received a copy of the GNU Affero General Public *
- License along with CertiVox MIRACL Crypto SDK. *
- If not, see . *
- *
-You can be released from the requirements of the license by purchasing *
-a commercial license. Buying such a license is mandatory as soon as you *
-develop commercial activities involving the CertiVox MIRACL Crypto SDK *
-without disclosing the source code of your own applications, or shipping *
-the CertiVox MIRACL Crypto SDK with a closed source product. *
- *
-***************************************************************************/
-/*
- *
- * MIRACL Core module - contains initialisation code and general purpose
- * utilities
- * mrcore.c
- *
- * Space can be saved by removing unneeded functions (mr_and ?)
- *
- */
-
-#include
-#include
-#include
-
-
-#ifdef MR_FP
-#include
-#endif
-
-
-/*** Multi-Threaded Support ***/
-
-#ifndef MR_GENERIC_MT
-
- #ifdef MR_OPENMP_MT
- #include
-
-#define MR_MIP_EXISTS
-
- miracl *mr_mip;
- #pragma omp threadprivate(mr_mip)
-
- miracl *get_mip()
- {
- return mr_mip;
- }
-
- void mr_init_threading()
- {
- }
-
- void mr_end_threading()
- {
- }
-
- #endif
-
- #ifdef MR_WINDOWS_MT
- #include
- DWORD mr_key;
-
- miracl *get_mip()
- {
- return (miracl *)TlsGetValue(mr_key);
- }
-
- void mr_init_threading()
- {
- mr_key=TlsAlloc();
- }
-
- void mr_end_threading()
- {
- TlsFree(mr_key);
- }
-
- #endif
-
- #ifdef MR_UNIX_MT
- #include
- pthread_key_t mr_key;
-
- miracl *get_mip()
- {
- return (miracl *)pthread_getspecific(mr_key);
- }
-
- void mr_init_threading()
- {
- pthread_key_create(&mr_key,(void(*)(void *))NULL);
- }
-
- void mr_end_threading()
- {
- pthread_key_delete(mr_key);
- }
- #endif
-
- #ifndef MR_WINDOWS_MT
- #ifndef MR_UNIX_MT
- #ifndef MR_OPENMP_MT
- #ifdef MR_STATIC
- miracl mip;
- miracl *mr_mip=&mip;
- #else
- miracl *mr_mip=NULL; /* MIRACL's one and only global variable */
- #endif
-#define MR_MIP_EXISTS
- miracl *get_mip()
- {
- return (miracl *)mr_mip;
- }
- #endif
- #endif
- #endif
-
-#ifdef MR_MIP_EXISTS
- void set_mip(miracl *mip)
- {
- mr_mip=mip;
- }
-#endif
-
-#endif
-
-/* See Advanced Windows by Jeffrey Richter, Chapter 12 for methods for
- creating different instances of this global for each executing thread
- when using Windows '95/NT
-*/
-
-#ifdef MR_STATIC
-
-#if MIRACL==8
-
-static const int mr_small_primes[]=
-{2,3,5,7,11,13,17,19,23,29,31,37,41,43,47,53,59,61,67,71,73,79,83,89,97,101,103,
-107,109,113,127,0};
-
-#else
-
-static const int mr_small_primes[]=
-{2,3,5,7,11,13,17,19,23,29,31,37,41,43,47,53,59,61,67,71,73,79,83,89,97,101,103,
-107,109,113,127,131,137,139,149,151,157,163,167,173,179,181,191,193,197,199,211,
-223,227,229,233,239,241,251,257,263,269,271,277,281,283,293,307,311,313,317,331,
-337,347,349,353,359,367,373,379,383,389,397,401,409,419,421,431,433,439,443,449,
-457,461,463,467,479,487,491,499,503,509,521,523,541,547,557,563,569,571,577,587,
-593,599,601,607,613,617,619,631,641,643,647,653,659,661,673,677,683,691,701,709,
-719,727,733,739,743,751,757,761,769,773,787,797,809,811,821,823,827,829,839,853,
-857,859,863,877,881,883,887,907,911,919,929,937,941,947,953,967,971,977,983,991,
-997,0};
-
-#endif
-
-#endif
-
-#ifndef MR_STRIPPED_DOWN
-#ifndef MR_NO_STANDARD_IO
-
-static char *names[] =
-{(char *)"your program",(char *)"innum",(char *)"otnum",(char *)"jack",(char *)"normalise",
-(char *)"multiply",(char *)"divide",(char *)"incr",(char *)"decr",(char *)"premult",
-(char *)"subdiv",(char *)"fdsize",(char *)"egcd",(char *)"cbase",
-(char *)"cinnum",(char *)"cotnum",(char *)"nroot",(char *)"power",
-(char *)"powmod",(char *)"bigdig",(char *)"bigrand",(char *)"nxprime",(char *)"isprime",
-(char *)"mirvar",(char *)"mad",(char *)"multi_inverse",(char *)"putdig",
-(char *)"add",(char *)"subtract",(char *)"mirsys",(char *)"xgcd",
-(char *)"fpack",(char *)"dconv",(char *)"mr_shift",(char *)"mround",(char *)"fmul",
-(char *)"fdiv",(char *)"fadd",(char *)"fsub",(char *)"fcomp",(char *)"fconv",
-(char *)"frecip",(char *)"fpmul",(char *)"fincr",(char *)"",(char *)"ftrunc",
-(char *)"frand",(char *)"sftbit",(char *)"build",(char *)"logb2",(char *)"expint",
-(char *)"fpower",(char *)"froot",(char *)"fpi",(char *)"fexp",(char *)"flog",(char *)"fpowf",
-(char *)"ftan",(char *)"fatan",(char *)"fsin",(char *)"fasin",(char *)"fcos",(char *)"facos",
-(char *)"ftanh",(char *)"fatanh",(char *)"fsinh",(char *)"fasinh",(char *)"fcosh",
-(char *)"facosh",(char *)"flop",(char *)"gprime",(char *)"powltr",(char *)"fft_mult",
-(char *)"crt_init",(char *)"crt",(char *)"otstr",(char *)"instr",(char *)"cotstr",(char *)"cinstr",(char *)"powmod2",
-(char *)"prepare_monty",(char *)"nres",(char *)"redc",(char *)"nres_modmult",(char *)"nres_powmod",
-(char *)"nres_moddiv",(char *)"nres_powltr",(char *)"divisible",(char *)"remain",
-(char *)"fmodulo",(char *)"nres_modadd",(char *)"nres_modsub",(char *)"nres_negate",
-(char *)"ecurve_init",(char *)"ecurve_add",(char *)"ecurve_mult",
-(char *)"epoint_init",(char *)"epoint_set",(char *)"epoint_get",(char *)"nres_powmod2",
-(char *)"nres_sqroot",(char *)"sqroot",(char *)"nres_premult",(char *)"ecurve_mult2",
-(char *)"ecurve_sub",(char *)"trial_division",(char *)"nxsafeprime",(char *)"nres_lucas",(char *)"lucas",
-(char *)"brick_init",(char *)"pow_brick",(char *)"set_user_function",
-(char *)"nres_powmodn",(char *)"powmodn",(char *)"ecurve_multn",
-(char *)"ebrick_init",(char *)"mul_brick",(char *)"epoint_norm",(char *)"nres_multi_inverse",(char *)"",
-(char *)"nres_dotprod",(char *)"epoint_negate",(char *)"ecurve_multi_add",
-(char *)"ecurve2_init",(char *)"",(char *)"epoint2_set",(char *)"epoint2_norm",(char *)"epoint2_get",
-(char *)"epoint2_comp",(char *)"ecurve2_add",(char *)"epoint2_negate",(char *)"ecurve2_sub",
-(char *)"ecurve2_multi_add",(char *)"ecurve2_mult",(char *)"ecurve2_multn",(char *)"ecurve2_mult2",
-(char *)"ebrick2_init",(char *)"mul2_brick",(char *)"prepare_basis",(char *)"strong_bigrand",
-(char *)"bytes_to_big",(char *)"big_to_bytes",(char *)"set_io_buffer_size",
-(char *)"epoint_getxyz",(char *)"epoint_double_add",(char *)"nres_double_inverse",
-(char *)"double_inverse",(char *)"epoint_x",(char *)"hamming",(char *)"expb2",(char *)"bigbits",
-(char *)"nres_lazy",(char *)"zzn2_imul",(char *)"nres_double_modadd",(char *)"nres_double_modsub",
-/*155*/(char *)"",(char *)"zzn2_from_int",(char *)"zzn2_negate",(char *)"zzn2_conj",(char *)"zzn2_add",
-(char *)"zzn2_sub",(char *)"zzn2_smul",(char *)"zzn2_mul",(char *)"zzn2_inv",(char *)"zzn2_timesi",(char *)"zzn2_powl",
-(char *)"zzn2_from_bigs",(char *)"zzn2_from_big",(char *)"zzn2_from_ints",
-(char *)"zzn2_sadd",(char *)"zzn2_ssub",(char *)"zzn2_times_irp",(char *)"zzn2_div2",
-(char *)"zzn3_from_int",(char *)"zzn3_from_ints",(char *)"zzn3_from_bigs",
-(char *)"zzn3_from_big",(char *)"zzn3_negate",(char *)"zzn3_powq",(char *)"zzn3_init",
-(char *)"zzn3_add",(char *)"zzn3_sadd",(char *)"zzn3_sub",(char *)"zzn3_ssub",(char *)"zzn3_smul",
-(char *)"zzn3_imul",(char *)"zzn3_mul",(char *)"zzn3_inv",(char *)"zzn3_div2",(char *)"zzn3_timesi",
-(char *)"epoint_multi_norm",(char *)"mr_jsf",(char *)"epoint2_multi_norm",
-(char *)"ecn2_compare",(char *)"ecn2_norm",(char *)"ecn2_set",(char *)"zzn2_txx",
-(char *)"zzn2_txd",(char *)"nres_div2",(char *)"nres_div3",(char *)"zzn2_div3",
-(char *)"ecn2_setx",(char *)"ecn2_rhs",(char *)"zzn2_qr",(char *)"zzn2_sqrt",(char *)"ecn2_add",(char *)"ecn2_mul2_jsf",(char *)"ecn2_mul",
-(char *)"nres_div5",(char *)"zzn2_div5",(char *)"zzn2_sqr",(char *)"ecn2_add_sub",(char *)"ecn2_psi",(char *)"invmodp",
-(char *)"zzn2_multi_inverse",(char *)"ecn2_multi_norm",(char *)"ecn2_precomp",(char *)"ecn2_mul4_gls_v",
-(char *)"ecn2_mul2",(char *)"ecn2_precomp_gls",(char *)"ecn2_mul2_gls",
-(char *)"ecn2_brick_init",(char *)"ecn2_mul_brick_gls",(char *)"ecn2_multn",(char *)"zzn3_timesi2",
-(char *)"nres_complex",(char *)"zzn4_from_int",(char *)"zzn4_negate",(char *)"zzn4_conj",(char *)"zzn4_add",(char *)"zzn4_sadd",(char *)"zzn4_sub",(char *)"zzn4_ssub",(char *)"zzn4_smul",(char *)"zzn4_sqr",
-(char *)"zzn4_mul",(char *)"zzn4_inv",(char *)"zzn4_div2",(char *)"zzn4_powq",(char *)"zzn4_tx",(char *)"zzn4_imul",(char *)"zzn4_lmul",(char *)"zzn4_from_big",
-(char *)"ecn2_mult4"};
-
-/* 0 - 243 (244 in all) */
-
-#endif
-#endif
-
-#ifdef MR_NOASM
-
-/* C only versions of muldiv/muldvd/muldvd2/muldvm */
-/* Note that mr_large should be twice the size of mr_small */
-
-mr_small muldiv(mr_small a,mr_small b,mr_small c,mr_small m,mr_small *rp)
-{
- mr_small q;
- mr_large ldres,p=(mr_large)a*b+c;
- q=(mr_small)(MR_LROUND(p/m));
- *rp=(mr_small)(p-(mr_large)q*m);
- return q;
-}
-
-#ifdef MR_FP_ROUNDING
-
-mr_small imuldiv(mr_small a,mr_small b,mr_small c,mr_small m,mr_large im,mr_small *rp)
-{
- mr_small q;
- mr_large ldres,p=(mr_large)a*b+c;
- q=(mr_small)MR_LROUND(p*im);
- *rp=(mr_small)(p-(mr_large)q*m);
- return q;
-}
-
-#endif
-
-#ifndef MR_NOFULLWIDTH
-
-mr_small muldvm(mr_small a,mr_small c,mr_small m,mr_small *rp)
-{
- mr_small q;
- union doubleword dble;
- dble.h[MR_BOT]=c;
- dble.h[MR_TOP]=a;
-
- q=(mr_small)(dble.d/m);
- *rp=(mr_small)(dble.d-(mr_large)q*m);
- return q;
-}
-
-mr_small muldvd(mr_small a,mr_small b,mr_small c,mr_small *rp)
-{
- union doubleword dble;
- dble.d=(mr_large)a*b+c;
-
- *rp=dble.h[MR_BOT];
- return dble.h[MR_TOP];
-}
-
-void muldvd2(mr_small a,mr_small b,mr_small *c,mr_small *rp)
-{
- union doubleword dble;
- dble.d=(mr_large)a*b+*c+*rp;
- *rp=dble.h[MR_BOT];
- *c=dble.h[MR_TOP];
-}
-
-#endif
-#endif
-
-#ifdef MR_NOFULLWIDTH
-
-/* no FULLWIDTH working, so supply dummies */
-
-/*
-
-mr_small muldvd(mr_small a,mr_small b,mr_small c,mr_small *rp)
-{
- return (mr_small)0;
-}
-
-mr_small muldvm(mr_small a,mr_small c,mr_small m,mr_small *rp)
-{
- return (mr_small)0;
-}
-
-void muldvd2(mr_small a,mr_small b,mr_small *c,mr_small *rp)
-{
-}
-
-*/
-
-#endif
-
-#ifndef MR_NO_STANDARD_IO
-
-static void mputs(char *s)
-{ /* output a string */
- int i=0;
- while (s[i]!=0) fputc((int)s[i++],stdout);
-}
-#endif
-
-void mr_berror(_MIPD_ int nerr)
-{ /* Big number error routine */
-#ifndef MR_STRIPPED_DOWN
-int i;
-#endif
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
-if (mr_mip->ERCON)
-{
- mr_mip->ERNUM=nerr;
- return;
-}
-#ifndef MR_NO_STANDARD_IO
-
-#ifndef MR_STRIPPED_DOWN
-mputs((char *)"\nMIRACL error from routine ");
-if (mr_mip->depthtrace[mr_mip->depth]]);
-else mputs((char *)"???");
-fputc('\n',stdout);
-
-for (i=mr_mip->depth-1;i>=0;i--)
-{
- mputs((char *)" called from ");
- if (itrace[i]]);
- else mputs((char *)"???");
- fputc('\n',stdout);
-}
-
-switch (nerr)
-{
-case 1 :
-mputs((char *)"Number base too big for representation\n");
-break;
-case 2 :
-mputs((char *)"Division by zero attempted\n");
-break;
-case 3 :
-mputs((char *)"Overflow - Number too big\n");
-break;
-case 4 :
-mputs((char *)"Internal result is negative\n");
-break;
-case 5 :
-mputs((char *)"Input format error\n");
-break;
-case 6 :
-mputs((char *)"Illegal number base\n");
-break;
-case 7 :
-mputs((char *)"Illegal parameter usage\n");
-break;
-case 8 :
-mputs((char *)"Out of space\n");
-break;
-case 9 :
-mputs((char *)"Even root of a negative number\n");
-break;
-case 10:
-mputs((char *)"Raising integer to negative power\n");
-break;
-case 11:
-mputs((char *)"Attempt to take illegal root\n");
-break;
-case 12:
-mputs((char *)"Integer operation attempted on Flash number\n");
-break;
-case 13:
-mputs((char *)"Flash overflow\n");
-break;
-case 14:
-mputs((char *)"Numbers too big\n");
-break;
-case 15:
-mputs((char *)"Log of a non-positive number\n");
-break;
-case 16:
-mputs((char *)"Flash to double conversion failure\n");
-break;
-case 17:
-mputs((char *)"I/O buffer overflow\n");
-break;
-case 18:
-mputs((char *)"MIRACL not initialised - no call to mirsys()\n");
-break;
-case 19:
-mputs((char *)"Illegal modulus \n");
-break;
-case 20:
-mputs((char *)"No modulus defined\n");
-break;
-case 21:
-mputs((char *)"Exponent too big\n");
-break;
-case 22:
-mputs((char *)"Unsupported Feature - check mirdef.h\n");
-break;
-case 23:
-mputs((char *)"Specified double length type isn't double length\n");
-break;
-case 24:
-mputs((char *)"Specified basis is NOT irreducible\n");
-break;
-case 25:
-mputs((char *)"Unable to control Floating-point rounding\n");
-break;
-case 26:
-mputs((char *)"Base must be binary (MR_ALWAYS_BINARY defined in mirdef.h ?)\n");
-break;
-case 27:
-mputs((char *)"No irreducible basis defined\n");
-break;
-case 28:
-mputs((char *)"Composite modulus\n");
-break;
-case 29:
-mputs((char *)"Input/output error when reading from RNG device node\n");
-break;
-default:
-mputs((char *)"Undefined error\n");
-break;
-}
-exit(0);
-#else
-mputs((char *)"MIRACL error\n");
-exit(0);
-#endif
-
-#endif
-}
-
-#ifndef MR_STRIPPED_DOWN
-
-void mr_track(_MIPDO_ )
-{ /* track course of program execution *
- * through the MIRACL routines */
-
-#ifndef MR_NO_STANDARD_IO
-
- int i;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- for (i=0;idepth;i++) fputc('-',stdout);
- fputc('>',stdout);
- mputs(names[mr_mip->trace[mr_mip->depth]]);
- fputc('\n',stdout);
-#endif
-}
-
-#endif
-
-#ifndef MR_NO_RAND
-
-mr_small brand(_MIPDO_ )
-{ /* Marsaglia & Zaman random number generator */
- int i,k;
- mr_unsign32 pdiff,t;
- mr_small r;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->lg2b>32)
- { /* underlying type is > 32 bits. Assume <= 64 bits */
- mr_mip->rndptr+=2;
- if (mr_mip->rndptrira[mr_mip->rndptr];
- r=mr_shiftbits(r,mr_mip->lg2b-32);
- r+=(mr_small)mr_mip->ira[mr_mip->rndptr+1];
- return r;
- }
- }
- else
- {
- mr_mip->rndptr++;
- if (mr_mip->rndptrira[mr_mip->rndptr];
- }
- mr_mip->rndptr=0;
- for (i=0,k=NK-NJ;iira[k];
- pdiff=t - mr_mip->ira[i] - mr_mip->borrow;
- if (pdiffborrow=0;
- if (pdiff>t) mr_mip->borrow=1;
- mr_mip->ira[i]=pdiff;
- }
- if (mr_mip->lg2b>32)
- { /* double up */
- r=(mr_small)mr_mip->ira[0];
- r=mr_shiftbits(r,mr_mip->lg2b-32);
- r+=(mr_small)mr_mip->ira[1];
- return r;
- }
- else return (mr_small)(mr_mip->ira[0]);
-}
-
-void irand(_MIPD_ mr_unsign32 seed)
-{ /* initialise random number system */
- int i,in;
- mr_unsign32 t,m=1L;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- mr_mip->borrow=0L;
- mr_mip->rndptr=0;
- mr_mip->ira[0]=seed;
- for (i=1;iira[in]=m;
- t=m;
- m=seed-m;
- seed=t;
- }
- for (i=0;i<1000;i++) brand(_MIPPO_ ); /* "warm-up" & stir the generator */
-}
-
-#endif
-
-mr_small mr_shiftbits(mr_small x,int n)
-{
-#ifdef MR_FP
- int i;
- mr_small dres;
- if (n==0) return x;
- if (n>0)
- {
- for (i=0;i0) x<<=n;
- else x>>=(-n);
- return x;
-#endif
-
-}
-
-mr_small mr_setbase(_MIPD_ mr_small nb)
-{ /* set base. Pack as many digits as *
- * possible into each computer word */
- mr_small temp;
-#ifdef MR_FP
- mr_small dres;
-#endif
-#ifndef MR_NOFULLWIDTH
- BOOL fits;
- int bits;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- fits=FALSE;
- bits=MIRACL;
- while (bits>1)
- {
- bits/=2;
- temp=((mr_small)1<apbase=nb;
- mr_mip->pack=MIRACL/bits;
- mr_mip->base=0;
- return 0;
- }
-#endif
- mr_mip->apbase=nb;
- mr_mip->pack=1;
- mr_mip->base=nb;
-#ifdef MR_SIMPLE_BASE
- return 0;
-#else
- if (mr_mip->base==0) return 0;
- temp=MR_DIV(MAXBASE,nb);
- while (temp>=nb)
- {
- temp=MR_DIV(temp,nb);
- mr_mip->base*=nb;
- mr_mip->pack++;
- }
-#ifdef MR_FP_ROUNDING
- mr_mip->inverse_base=mr_invert(mr_mip->base);
- return mr_mip->inverse_base;
-#else
- return 0;
-#endif
-#endif
-}
-
-#ifdef MR_FLASH
-
-BOOL fit(big x,big y,int f)
-{ /* returns TRUE if x/y would fit flash format of length f */
- int n,d;
- n=(int)(x->len&(MR_OBITS));
- d=(int)(y->len&(MR_OBITS));
- if (n==1 && x->w[0]==1) n=0;
- if (d==1 && y->w[0]==1) d=0;
- if (n+d<=f) return TRUE;
- return FALSE;
-}
-
-#endif
-
-int mr_lent(flash x)
-{ /* return length of big or flash in words */
- mr_lentype lx;
- lx=(x->len&(MR_OBITS));
-#ifdef MR_FLASH
- return (int)((lx&(MR_MSK))+((lx>>(MR_BTS))&(MR_MSK)));
-#else
- return (int)lx;
-#endif
-}
-
-void zero(flash x)
-{ /* set big/flash number to zero */
- int i,n;
- mr_small *g;
- if (x==NULL) return;
-#ifdef MR_FLASH
- n=mr_lent(x);
-#else
- n=(x->len&MR_OBITS);
-#endif
- g=x->w;
-
- for (i=0;ilen=0;
-}
-
-void uconvert(_MIPD_ unsigned int n ,big x)
-{ /* convert unsigned integer n to big number format */
- int m;
-#ifdef MR_FP
- mr_small dres;
-#endif
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- zero(x);
- if (n==0) return;
-
- m=0;
-#ifndef MR_SIMPLE_BASE
- if (mr_mip->base==0)
- {
-#endif
-#ifndef MR_NOFULLWIDTH
-#if MR_IBITS > MIRACL
- while (n>0)
- {
- x->w[m++]=(mr_small)(n%((mr_small)1<<(MIRACL)));
- n/=((mr_small)1<<(MIRACL));
- }
-#else
- x->w[m++]=(mr_small)n;
-#endif
-#endif
-#ifndef MR_SIMPLE_BASE
- }
- else while (n>0)
- {
- x->w[m++]=MR_REMAIN((mr_small)n,mr_mip->base);
- n=(unsigned int)((mr_small)n/mr_mip->base);
- }
-#endif
- x->len=m;
-}
-
-void tconvert(_MIPD_ mr_utype n,big x)
-{
- mr_lentype s;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (n==0) {zero(x); return;}
- s=0;
- if (n<0)
- {
- s=MR_MSBIT;
- n=(-n);
- }
- x->w[0]=n;
- x->len=1;
- x->len|=s;
-}
-
-void convert(_MIPD_ int n ,big x)
-{ /* convert signed integer n to big number format */
- mr_lentype s;
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (n==0) {zero(x); return;}
- s=0;
- if (n<0)
- {
- s=MR_MSBIT;
- n=(-n);
- }
- uconvert(_MIPP_ (unsigned int)n,x);
- x->len|=s;
-}
-
-#ifndef MR_STATIC
-#ifdef mr_dltype
-
-void dlconv(_MIPD_ mr_dltype n,big x)
-{ /* convert double length integer to big number format - rarely needed */
- int m;
- mr_lentype s;
-#ifdef MR_FP
- mr_small dres;
-#endif
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- zero(x);
- if (n==0) return;
- s=0;
- if (n<0)
- {
- s=MR_MSBIT;
- n=(-n);
- }
- m=0;
-#ifndef MR_SIMPLE_BASE
- if (mr_mip->base==0)
- {
-#endif
-#ifndef MR_NOFULLWIDTH
- while (n>0)
- {
- x->w[m++]=(mr_small)(n%((mr_dltype)1<<(MIRACL)));
- n/=((mr_dltype)1<<(MIRACL));
- }
-#endif
-#ifndef MR_SIMPLE_BASE
- }
- else while (n>0)
- {
- x->w[m++]=(mr_small)MR_REMAIN(n,mr_mip->base);
- n/=mr_mip->base;
- }
-#endif
- x->len=(m|s);
-}
-
-#endif
-
-void ulgconv(_MIPD_ unsigned long n,big x)
-{ /* convert unsigned long integer to big number format - rarely needed */
- int m;
-#ifdef MR_FP
- mr_small dres;
-#endif
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- zero(x);
- if (n==0) return;
-
- m=0;
-#ifndef MR_SIMPLE_BASE
- if (mr_mip->base==0)
- {
-#endif
-#ifndef MR_NOFULLWIDTH
-#if MR_LBITS > MIRACL
- while (n>0)
- {
- x->w[m++]=(mr_small)(n%(1L<<(MIRACL)));
- n/=(1L<<(MIRACL));
- }
-#else
- x->w[m++]=(mr_small)n;
-#endif
-#endif
-#ifndef MR_SIMPLE_BASE
- }
- else while (n>0)
- {
- x->w[m++]=MR_REMAIN(n,mr_mip->base);
- n=(unsigned long)((mr_small)n/mr_mip->base);
- }
-#endif
- x->len=m;
-}
-
-void lgconv(_MIPD_ long n,big x)
-{ /* convert signed long integer to big number format - rarely needed */
- mr_lentype s;
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (n==0) {zero(x); return;}
- s=0;
- if (n<0)
- {
- s=MR_MSBIT;
- n=(-n);
- }
- ulgconv(_MIPP_ (unsigned long)n,x);
-
- x->len|=s;
-}
-
-flash mirvar(_MIPD_ int iv)
-{ /* initialize big/flash number */
- flash x;
- int align;
- char *ptr;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- if (mr_mip->ERNUM) return NULL;
- MR_IN(23);
-
- if (!(mr_mip->active))
- {
- mr_berror(_MIPP_ MR_ERR_NO_MIRSYS);
- MR_OUT
- return NULL;
- }
-
-/* OK, now I control alignment.... */
-
-/* Allocate space for big, the length, the pointer, and the array */
-/* Do it all in one memory allocation - this is quicker */
-/* Ensure that the array has correct alignment */
-
- x=(big)mr_alloc(_MIPP_ mr_size(mr_mip->nib-1),1);
- if (x==NULL)
- {
- MR_OUT
- return x;
- }
-
- ptr=(char *)&x->w;
- align=(unsigned long)(ptr+sizeof(mr_small *))%sizeof(mr_small);
-
- x->w=(mr_small *)(ptr+sizeof(mr_small *)+sizeof(mr_small)-align);
-
- if (iv!=0) convert(_MIPP_ iv,x);
- MR_OUT
- return x;
-}
-
-#endif
-
-flash mirvar_mem_variable(char *mem,int index,int sz)
-{
- flash x;
- int align;
- char *ptr;
- int offset,r;
-
-/* alignment */
- offset=0;
- r=(unsigned long)mem%MR_SL;
- if (r>0) offset=MR_SL-r;
-
- x=(big)&mem[offset+mr_size(sz)*index];
- ptr=(char *)&x->w;
- align=(unsigned long)(ptr+sizeof(mr_small *))%sizeof(mr_small);
- x->w=(mr_small *)(ptr+sizeof(mr_small *)+sizeof(mr_small)-align);
-
- return x;
-}
-
-flash mirvar_mem(_MIPD_ char *mem,int index)
-{ /* initialize big/flash number from pre-allocated memory */
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- if (mr_mip->ERNUM) return NULL;
-
- return mirvar_mem_variable(mem,index,mr_mip->nib-1);
-
-}
-
-void set_user_function(_MIPD_ BOOL (*user)(void))
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(111)
-
- if (!(mr_mip->active))
- {
- mr_berror(_MIPP_ MR_ERR_NO_MIRSYS);
- MR_OUT
- return;
- }
-
- mr_mip->user=user;
-
- MR_OUT
-}
-
-#ifndef MR_STATIC
-
-#ifndef MR_SIMPLE_IO
-
-void set_io_buffer_size(_MIPD_ int len)
-{
- int i;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (len<0) return;
- MR_IN(142)
- for (i=0;iIOBSIZ;i++) mr_mip->IOBUFF[i]=0;
- mr_free(mr_mip->IOBUFF);
- if (len==0)
- {
- MR_OUT
- return;
- }
- mr_mip->IOBSIZ=len;
- mr_mip->IOBUFF=(char *)mr_alloc(_MIPP_ len+1,1);
- mr_mip->IOBUFF[0]='\0';
- MR_OUT
-}
-#endif
-
-#endif
-
-/* Initialise a big from ROM given its fixed length */
-
-BOOL init_big_from_rom(big x,int len,const mr_small *rom,int romsize,int *romptr)
-{
- int i;
- zero(x);
- x->len=len;
- for (i=0;i=romsize) return FALSE;
-#ifdef MR_AVR
- x->w[i]=pgm_read_byte_near(&rom[*romptr]);
-#else
- x->w[i]=rom[*romptr];
-#endif
- (*romptr)++;
- }
-
- mr_lzero(x);
- return TRUE;
-}
-
-/* Initialise an elliptic curve point from ROM */
-
-BOOL init_point_from_rom(epoint *P,int len,const mr_small *rom,int romsize,int *romptr)
-{
- if (!init_big_from_rom(P->X,len,rom,romsize,romptr)) return FALSE;
- if (!init_big_from_rom(P->Y,len,rom,romsize,romptr)) return FALSE;
- P->marker=MR_EPOINT_NORMALIZED;
- return TRUE;
-}
-
-#ifdef MR_GENERIC_AND_STATIC
-miracl *mirsys(miracl *mr_mip,int nd,mr_small nb)
-#else
-miracl *mirsys(int nd,mr_small nb)
-#endif
-{ /* Initialize MIRACL system to *
- * use numbers to base nb, and *
- * nd digits or (-nd) bytes long */
-
-/* In these cases mr_mip is passed as the first parameter */
-
-#ifdef MR_GENERIC_AND_STATIC
- return mirsys_basic(mr_mip,nd,nb);
-#endif
-
-#ifdef MR_GENERIC_MT
-#ifndef MR_STATIC
- miracl *mr_mip=mr_first_alloc();
- return mirsys_basic(mr_mip,nd,nb);
-#endif
-#endif
-/* In these cases mr_mip is a "global" pointer and the mip itself is allocated from the heap.
- In fact mr_mip (and mip) may be thread specific if some multi-threading scheme is implemented */
-#ifndef MR_STATIC
- #ifdef MR_WINDOWS_MT
- miracl *mr_mip=mr_first_alloc();
- TlsSetValue(mr_key,mr_mip);
- #endif
-
- #ifdef MR_UNIX_MT
- miracl *mr_mip=mr_first_alloc();
- pthread_setspecific(mr_key,mr_mip);
- #endif
-
- #ifdef MR_OPENMP_MT
- mr_mip=mr_first_alloc();
- #endif
-
- #ifndef MR_WINDOWS_MT
- #ifndef MR_UNIX_MT
- #ifndef MR_OPENMP_MT
- mr_mip=mr_first_alloc();
- #endif
- #endif
- #endif
-#endif
-
-#ifndef MR_GENERIC_MT
- mr_mip=get_mip();
-#endif
- return mirsys_basic(mr_mip,nd,nb);
-}
-
-miracl *mirsys_basic(miracl *mr_mip,int nd,mr_small nb)
-{
-#ifndef MR_NO_RAND
- int i;
-#endif
-
- mr_small b,nw;
-#ifdef MR_FP
- mr_small dres;
-#endif
-
- if (mr_mip==NULL) return NULL;
-
-#ifndef MR_STRIPPED_DOWN
- mr_mip->depth=0;
- mr_mip->trace[0]=0;
- mr_mip->depth++;
- mr_mip->trace[mr_mip->depth]=29;
-#endif
- /* digest hardware configuration */
-
-#ifdef MR_NO_STANDARD_IO
- mr_mip->ERCON=TRUE;
-#else
- mr_mip->ERCON=FALSE;
-#endif
-#ifndef MR_STATIC
- mr_mip->logN=0;
- mr_mip->degree=0;
- mr_mip->chin.NP=0;
-#endif
-
-
- mr_mip->user=NULL;
- mr_mip->same=FALSE;
- mr_mip->first_one=FALSE;
- mr_mip->debug=FALSE;
- mr_mip->AA=0;
-#ifndef MR_AFFINE_ONLY
- mr_mip->coord=MR_NOTSET;
-#endif
-
-#ifdef MR_NOFULLWIDTH
- if (nb==0)
- {
- mr_berror(_MIPP_ MR_ERR_BAD_BASE);
- MR_OUT
- return mr_mip;
- }
-#endif
-
-#ifndef MR_FP
-#ifdef mr_dltype
-#ifndef MR_NOFULLWIDTH
- if (sizeof(mr_dltype)<2*sizeof(mr_utype))
- { /* double length type, isn't */
- mr_berror(_MIPP_ MR_ERR_NOT_DOUBLE_LEN);
- MR_OUT
- return mr_mip;
- }
-#endif
-#endif
-#endif
-
- if (nb==1 || nb>MAXBASE)
- {
- mr_berror(_MIPP_ MR_ERR_BAD_BASE);
- MR_OUT
- return mr_mip;
- }
-
-#ifdef MR_FP_ROUNDING
- if (mr_setbase(_MIPP_ nb)==0)
- { /* unable in fact to control FP rounding */
- mr_berror(_MIPP_ MR_ERR_NO_ROUNDING);
- MR_OUT
- return mr_mip;
- }
-#else
- mr_setbase(_MIPP_ nb);
-#endif
-
- b=mr_mip->base;
-
-#ifdef MR_SIMPLE_BASE
- if (b!=0)
- {
- mr_berror(_MIPP_ MR_ERR_BAD_BASE);
- MR_OUT
- return mr_mip;
- }
-#endif
-
- mr_mip->lg2b=0;
- mr_mip->base2=1;
-#ifndef MR_SIMPLE_BASE
- if (b==0)
- {
-#endif
- mr_mip->lg2b=MIRACL;
- mr_mip->base2=0;
-#ifndef MR_SIMPLE_BASE
- }
- else while (b>1)
- {
- b=MR_DIV(b,2);
- mr_mip->lg2b++;
- mr_mip->base2*=2;
- }
-#endif
-
-#ifdef MR_ALWAYS_BINARY
- if (mr_mip->base!=mr_mip->base2)
- {
- mr_berror(_MIPP_ MR_ERR_NOT_BINARY);
- MR_OUT
- return mr_mip;
- }
-#endif
-
-/* calculate total space for bigs */
-/*
-
- big -> |int len|small *ptr| alignment space | size in words +1| alignment up to multiple of 4 |
-
-
-*/
- if (nd>0) nw=MR_ROUNDUP(nd,mr_mip->pack);
- else nw=MR_ROUNDUP(8*(-nd),mr_mip->lg2b);
-
- if (nw<1) nw=1;
- mr_mip->nib=(int)(nw+1); /* add one extra word for small overflows */
-
-#ifdef MR_STATIC
- if (nw>MR_STATIC)
- {
- mr_berror(_MIPP_ MR_ERR_TOO_BIG);
- MR_OUT
- return mr_mip;
- }
-#endif
-
- /* mr_mip->nib=(int)(nw+1); add one extra word for small overflows */
-
-#ifdef MR_FLASH
- mr_mip->workprec=mr_mip->nib;
- mr_mip->stprec=mr_mip->nib;
- while (mr_mip->stprec>2 && mr_mip->stprec>MR_FLASH/mr_mip->lg2b)
- mr_mip->stprec=(mr_mip->stprec+1)/2;
- if (mr_mip->stprec<2) mr_mip->stprec=2;
-
-#endif
-
-#ifndef MR_DOUBLE_BIG
- mr_mip->check=ON;
-#else
- mr_mip->check=OFF;
-#endif
-
-#ifndef MR_SIMPLE_BASE
-#ifndef MR_SIMPLE_IO
- mr_mip->IOBASE=10; /* defaults */
-#endif
-#endif
- mr_mip->ERNUM=0;
-
- mr_mip->NTRY=6;
- mr_mip->MONTY=ON;
-#ifdef MR_FLASH
- mr_mip->EXACT=TRUE;
- mr_mip->RPOINT=OFF;
-#endif
-#ifndef MR_STRIPPED_DOWN
- mr_mip->TRACER=OFF;
-#endif
-
-#ifndef MR_SIMPLE_IO
- mr_mip->INPLEN=0;
- mr_mip->IOBSIZ=MR_DEFAULT_BUFFER_SIZE;
-#endif
-
-#ifdef MR_STATIC
- mr_mip->PRIMES=mr_small_primes;
-#else
- mr_mip->PRIMES=NULL;
-#ifndef MR_SIMPLE_IO
- mr_mip->IOBUFF=(char *)mr_alloc(_MIPP_ MR_DEFAULT_BUFFER_SIZE+1,1);
-#endif
-#endif
-#ifndef MR_SIMPLE_IO
- mr_mip->IOBUFF[0]='\0';
-#endif
- mr_mip->qnr=0;
- mr_mip->cnr=0;
- mr_mip->TWIST=0;
- mr_mip->pmod8=0;
- mr_mip->pmod9=0;
-
-/* quick start for rng. irand(.) should be called first before serious use.. */
-
-#ifndef MR_NO_RAND
- mr_mip->ira[0]=0x55555555;
- mr_mip->ira[1]=0x12345678;
-
- for (i=2;iira[i]=mr_mip->ira[i-1]+mr_mip->ira[i-2]+0x1379BDF1;
- mr_mip->rndptr=NK;
- mr_mip->borrow=0;
-#endif
-
- mr_mip->nib=2*mr_mip->nib+1;
-#ifdef MR_FLASH
- if (mr_mip->nib!=(mr_mip->nib&(MR_MSK)))
-#else
- if (mr_mip->nib!=(int)(mr_mip->nib&(MR_OBITS)))
-#endif
- {
- mr_berror(_MIPP_ MR_ERR_TOO_BIG);
- mr_mip->nib=(mr_mip->nib-1)/2;
- MR_OUT
- return mr_mip;
- }
-#ifndef MR_STATIC
- mr_mip->workspace=(char *)memalloc(_MIPP_ MR_SPACES); /* grab workspace */
-#else
- memset(mr_mip->workspace,0,MR_BIG_RESERVE(MR_SPACES));
-#endif
-
- mr_mip->M=0;
- mr_mip->fin=FALSE;
- mr_mip->fout=FALSE;
- mr_mip->active=ON;
-
- mr_mip->nib=(mr_mip->nib-1)/2;
-
-/* allocate memory for workspace variables */
-
-#ifndef MR_DOUBLE_BIG
-
- mr_mip->w0=mirvar_mem(_MIPP_ mr_mip->workspace,0); /* double length */
- mr_mip->w1=mirvar_mem(_MIPP_ mr_mip->workspace,2);
- mr_mip->w2=mirvar_mem(_MIPP_ mr_mip->workspace,3);
- mr_mip->w3=mirvar_mem(_MIPP_ mr_mip->workspace,4);
- mr_mip->w4=mirvar_mem(_MIPP_ mr_mip->workspace,5);
- mr_mip->w5=mirvar_mem(_MIPP_ mr_mip->workspace,6); /* double length */
- mr_mip->w6=mirvar_mem(_MIPP_ mr_mip->workspace,8); /* double length */
- mr_mip->w7=mirvar_mem(_MIPP_ mr_mip->workspace,10); /* double length */
- mr_mip->w8=mirvar_mem(_MIPP_ mr_mip->workspace,12);
- mr_mip->w9=mirvar_mem(_MIPP_ mr_mip->workspace,13);
- mr_mip->w10=mirvar_mem(_MIPP_ mr_mip->workspace,14);
- mr_mip->w11=mirvar_mem(_MIPP_ mr_mip->workspace,15);
- mr_mip->w12=mirvar_mem(_MIPP_ mr_mip->workspace,16);
- mr_mip->w13=mirvar_mem(_MIPP_ mr_mip->workspace,17);
- mr_mip->w14=mirvar_mem(_MIPP_ mr_mip->workspace,18);
- mr_mip->w15=mirvar_mem(_MIPP_ mr_mip->workspace,19);
- mr_mip->sru=mirvar_mem(_MIPP_ mr_mip->workspace,20);
- mr_mip->modulus=mirvar_mem(_MIPP_ mr_mip->workspace,21);
- mr_mip->pR=mirvar_mem(_MIPP_ mr_mip->workspace,22); /* double length */
- mr_mip->A=mirvar_mem(_MIPP_ mr_mip->workspace,24);
- mr_mip->B=mirvar_mem(_MIPP_ mr_mip->workspace,25);
- mr_mip->one=mirvar_mem(_MIPP_ mr_mip->workspace,26);
-#ifdef MR_KCM
- mr_mip->big_ndash=mirvar_mem(_MIPP_ mr_mip->workspace,27);
- mr_mip->ws=mirvar_mem(_MIPP_ mr_mip->workspace,28);
- mr_mip->wt=mirvar_mem(_MIPP_ mr_mip->workspace,29); /* double length */
-#endif
-#ifdef MR_FLASH
-#ifdef MR_KCM
- mr_mip->pi=mirvar_mem(_MIPP_ mr_mip->workspace,31);
-#else
- mr_mip->pi=mirvar_mem(_MIPP_ mr_mip->workspace,27);
-#endif
-#endif
-
-#else
-/* w0-w7 are double normal length */
- mr_mip->w0=mirvar_mem(_MIPP_ mr_mip->workspace,0); /* quad length */
- mr_mip->w1=mirvar_mem(_MIPP_ mr_mip->workspace,4); /* double length */
- mr_mip->w2=mirvar_mem(_MIPP_ mr_mip->workspace,6);
- mr_mip->w3=mirvar_mem(_MIPP_ mr_mip->workspace,8);
- mr_mip->w4=mirvar_mem(_MIPP_ mr_mip->workspace,10);
- mr_mip->w5=mirvar_mem(_MIPP_ mr_mip->workspace,12); /* quad length */
- mr_mip->w6=mirvar_mem(_MIPP_ mr_mip->workspace,16); /* quad length */
- mr_mip->w7=mirvar_mem(_MIPP_ mr_mip->workspace,20); /* quad length */
- mr_mip->w8=mirvar_mem(_MIPP_ mr_mip->workspace,24);
-
- mr_mip->w9=mirvar_mem(_MIPP_ mr_mip->workspace,25);
- mr_mip->w10=mirvar_mem(_MIPP_ mr_mip->workspace,26);
- mr_mip->w11=mirvar_mem(_MIPP_ mr_mip->workspace,27);
- mr_mip->w12=mirvar_mem(_MIPP_ mr_mip->workspace,28);
- mr_mip->w13=mirvar_mem(_MIPP_ mr_mip->workspace,29);
- mr_mip->w14=mirvar_mem(_MIPP_ mr_mip->workspace,30);
- mr_mip->w15=mirvar_mem(_MIPP_ mr_mip->workspace,31);
- mr_mip->sru=mirvar_mem(_MIPP_ mr_mip->workspace,32);
- mr_mip->modulus=mirvar_mem(_MIPP_ mr_mip->workspace,33);
- mr_mip->pR=mirvar_mem(_MIPP_ mr_mip->workspace,34); /* double length */
- mr_mip->A=mirvar_mem(_MIPP_ mr_mip->workspace,36);
- mr_mip->B=mirvar_mem(_MIPP_ mr_mip->workspace,37);
- mr_mip->one=mirvar_mem(_MIPP_ mr_mip->workspace,38);
-#ifdef MR_KCM
- mr_mip->big_ndash=mirvar_mem(_MIPP_ mr_mip->workspace,39);
- mr_mip->ws=mirvar_mem(_MIPP_ mr_mip->workspace,40);
- mr_mip->wt=mirvar_mem(_MIPP_ mr_mip->workspace,41); /* double length */
-#endif
-#ifdef MR_FLASH
-#ifdef MR_KCM
- mr_mip->pi=mirvar_mem(_MIPP_ mr_mip->workspace,43);
-#else
- mr_mip->pi=mirvar_mem(_MIPP_ mr_mip->workspace,39);
-#endif
-#endif
-
-#endif
- MR_OUT
- return mr_mip;
-}
-
-#ifndef MR_STATIC
-
-/* allocate space for a number of bigs from the heap */
-
-void *memalloc(_MIPD_ int num)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- return mr_alloc(_MIPP_ mr_big_reserve(num,mr_mip->nib-1),1);
-}
-
-#endif
-
-void memkill(_MIPD_ char *mem,int len)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mem==NULL) return;
- memset(mem,0,mr_big_reserve(len,mr_mip->nib-1));
-#ifndef MR_STATIC
- mr_free(mem);
-#endif
-}
-
-#ifndef MR_STATIC
-
-void mirkill(big x)
-{ /* kill a big/flash variable, that is set it to zero
- and free its memory */
- if (x==NULL) return;
- zero(x);
- mr_free(x);
-}
-
-#endif
-
-void mirexit(_MIPDO_ )
-{ /* clean up after miracl */
-
- int i;
-#ifdef MR_WINDOWS_MT
- miracl *mr_mip=get_mip();
-#endif
-#ifdef MR_UNIX_MT
- miracl *mr_mip=get_mip();
-#endif
-#ifdef MR_OPENMP_MT
- miracl *mr_mip=get_mip();
-#endif
- mr_mip->ERCON=FALSE;
- mr_mip->active=OFF;
- memkill(_MIPP_ mr_mip->workspace,MR_SPACES);
-#ifndef MR_NO_RAND
- for (i=0;iira[i]=0L;
-#endif
-#ifndef MR_STATIC
-#ifndef MR_SIMPLE_IO
- set_io_buffer_size(_MIPP_ 0);
-#endif
- if (mr_mip->PRIMES!=NULL) mr_free(mr_mip->PRIMES);
-#else
-#ifndef MR_SIMPLE_IO
- for (i=0;i<=MR_DEFAULT_BUFFER_SIZE;i++)
- mr_mip->IOBUFF[i]=0;
-#endif
-#endif
-
-#ifndef MR_STATIC
- mr_free(mr_mip);
-#ifdef MR_WINDOWS_MT
- TlsSetValue(mr_key, NULL); /* Thank you Thales */
-#endif
-#endif
-
-#ifndef MR_GENERIC_MT
-#ifndef MR_WINDOWS_MT
-#ifndef MR_UNIX_MT
-#ifndef MR_STATIC
- mr_mip=NULL;
-#endif
-#endif
-#endif
-#endif
-
-#ifdef MR_OPENMP_MT
- mr_mip=NULL;
-#endif
-
-}
-
-int exsign(flash x)
-{ /* extract sign of big/flash number */
- if ((x->len&(MR_MSBIT))==0) return PLUS;
- else return MINUS;
-}
-
-void insign(int s,flash x)
-{ /* assert sign of big/flash number */
- if (x->len==0) return;
- if (s<0) x->len|=MR_MSBIT;
- else x->len&=MR_OBITS;
-}
-
-void mr_lzero(big x)
-{ /* strip leading zeros from big number */
- mr_lentype s;
- int m;
- s=(x->len&(MR_MSBIT));
- m=(int)(x->len&(MR_OBITS));
- while (m>0 && x->w[m-1]==0)
- m--;
- x->len=m;
- if (m>0) x->len|=s;
-}
-
-#ifndef MR_SIMPLE_IO
-
-int getdig(_MIPD_ big x,int i)
-{ /* extract a packed digit */
- int k;
- mr_small n;
-#ifdef MR_FP
- mr_small dres;
-#endif
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- i--;
- n=x->w[i/mr_mip->pack];
-
- if (mr_mip->pack==1) return (int)n;
- k=i%mr_mip->pack;
- for (i=1;i<=k;i++)
- n=MR_DIV(n,mr_mip->apbase);
- return (int)MR_REMAIN(n,mr_mip->apbase);
-}
-
-int numdig(_MIPD_ big x)
-{ /* returns number of digits in x */
- int nd;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- if (x->len==0) return 0;
-
- nd=(int)(x->len&(MR_OBITS))*mr_mip->pack;
- while (getdig(_MIPP_ x,nd)==0)
- nd--;
- return nd;
-}
-
-void putdig(_MIPD_ int n,big x,int i)
-{ /* insert a digit into a packed word */
- int j,k,lx;
- mr_small m,p;
- mr_lentype s;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(26)
-
- s=(x->len&(MR_MSBIT));
- lx=(int)(x->len&(MR_OBITS));
- m=getdig(_MIPP_ x,i);
- p=n;
- i--;
- j=i/mr_mip->pack;
- k=i%mr_mip->pack;
- for (i=1;i<=k;i++)
- {
- m*=mr_mip->apbase;
- p*=mr_mip->apbase;
- }
- if (j>=mr_mip->nib && (mr_mip->check || j>=2*mr_mip->nib))
- {
- mr_berror(_MIPP_ MR_ERR_OVERFLOW);
- MR_OUT
- return;
- }
-
- x->w[j]=(x->w[j]-m)+p;
- if (j>=lx) x->len=((j+1)|s);
- mr_lzero(x);
- MR_OUT
-}
-
-#endif
-
-#ifndef MR_FP
-
-void mr_and(big x,big y,big z)
-{ /* z= bitwise logical AND of x and y */
- int i,nx,ny,nz,nr;
- if (x==y)
- {
- copy(x,z);
- return;
- }
-
-#ifdef MR_FLASH
- nx=mr_lent(x);
- ny=mr_lent(y);
- nz=mr_lent(z);
-#else
- ny=(y->len&(MR_OBITS));
- nx=(x->len&(MR_OBITS));
- nz=(z->len&(MR_OBITS));
-#endif
- if (nyw[i]=x->w[i]&y->w[i];
- for (i=nr;iw[i]=0;
- z->len=nr;
-}
-
-void mr_xor(big x,big y,big z)
-{
- int i,nx,ny,nz,nr;
- if (x==y)
- {
- copy(x,z);
- return;
- }
-
-#ifdef MR_FLASH
- nx=mr_lent(x);
- ny=mr_lent(y);
- nz=mr_lent(z);
-#else
- ny=(y->len&(MR_OBITS));
- nx=(x->len&(MR_OBITS));
- nz=(z->len&(MR_OBITS));
-#endif
- if (nyw[i]=x->w[i]^y->w[i];
- for (i=nr;iw[i]=0;
- z->len=nr;
-}
-
-#endif
-
-void copy(flash x,flash y)
-{ /* copy x to y: y=x */
- int i,nx,ny;
- mr_small *gx,*gy;
- if (x==y || y==NULL) return;
-
- if (x==NULL)
- {
- zero(y);
- return;
- }
-
-#ifdef MR_FLASH
- ny=mr_lent(y);
- nx=mr_lent(x);
-#else
- ny=(y->len&(MR_OBITS));
- nx=(x->len&(MR_OBITS));
-#endif
-
- gx=x->w;
- gy=y->w;
-
- for (i=nx;ilen=x->len;
-
-}
-
-void negify(flash x,flash y)
-{ /* negate a big/flash variable: y=-x */
- copy(x,y);
- if (y->len!=0) y->len^=MR_MSBIT;
-}
-
-void absol(flash x,flash y)
-{ /* y=abs(x) */
- copy(x,y);
- y->len&=MR_OBITS;
-}
-
-BOOL mr_notint(flash x)
-{ /* returns TRUE if x is Flash */
-#ifdef MR_FLASH
- if ((((x->len&(MR_OBITS))>>(MR_BTS))&(MR_MSK))!=0) return TRUE;
-#endif
- return FALSE;
-}
-
-void mr_shift(_MIPD_ big x,int n,big w)
-{ /* set w=x.(mr_base^n) by shifting */
- mr_lentype s;
- int i,bl;
- mr_small *gw=w->w;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
- copy(x,w);
- if (w->len==0 || n==0) return;
- MR_IN(33)
-
- if (mr_notint(w)) mr_berror(_MIPP_ MR_ERR_INT_OP);
- s=(w->len&(MR_MSBIT));
- bl=(int)(w->len&(MR_OBITS))+n;
- if (bl<=0)
- {
- zero(w);
- MR_OUT
- return;
- }
- if (bl>mr_mip->nib && mr_mip->check) mr_berror(_MIPP_ MR_ERR_OVERFLOW);
- if (mr_mip->ERNUM)
- {
- MR_OUT
- return;
- }
- if (n>0)
- {
- for (i=bl-1;i>=n;i--)
- gw[i]=gw[i-n];
- for (i=0;ilen=(bl|s);
- MR_OUT
-}
-
-int size(big x)
-{ /* get size of big number; convert to *
- * integer - if possible */
- int n,m;
- mr_lentype s;
- if (x==NULL) return 0;
- s=(x->len&MR_MSBIT);
- m=(int)(x->len&MR_OBITS);
- if (m==0) return 0;
- if (m==1 && x->w[0]<(mr_small)MR_TOOBIG) n=(int)x->w[0];
- else n=MR_TOOBIG;
- if (s==MR_MSBIT) return (-n);
- return n;
-}
-
-int mr_compare(big x,big y)
-{ /* compare x and y: =1 if x>y =-1 if xlen&MR_MSBIT);
- sy=(y->len&MR_MSBIT);
- if (sx==0) sig=PLUS;
- else sig=MINUS;
- if (sx!=sy) return sig;
- m=(int)(x->len&MR_OBITS);
- n=(int)(y->len&MR_OBITS);
- if (m>n) return sig;
- if (m0)
- { /* check digit by digit */
- m--;
- if (x->w[m]>y->w[m]) return sig;
- if (x->w[m]w[m]) return -sig;
- }
- return 0;
-}
-
-#ifdef MR_FLASH
-
-void fpack(_MIPD_ big n,big d,flash x)
-{ /* create floating-slash number x=n/d from *
- * big integer numerator and denominator */
- mr_lentype s;
- int i,ld,ln;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(31)
-
- ld=(int)(d->len&MR_OBITS);
- if (ld==0) mr_berror(_MIPP_ MR_ERR_FLASH_OVERFLOW);
- if (ld==1 && d->w[0]==1) ld=0;
- if (x==d) mr_berror(_MIPP_ MR_ERR_BAD_PARAMETERS);
- if (mr_notint(n) || mr_notint(d)) mr_berror(_MIPP_ MR_ERR_INT_OP);
- s=(n->len&MR_MSBIT);
- ln=(int)(n->len&MR_OBITS);
- if (ln==1 && n->w[0]==1) ln=0;
- if ((ld+ln>mr_mip->nib) && (mr_mip->check || ld+ln>2*mr_mip->nib))
- mr_berror(_MIPP_ MR_ERR_FLASH_OVERFLOW);
- if (mr_mip->ERNUM)
- {
- MR_OUT
- return;
- }
- copy(n,x);
- if (n->len==0)
- {
- MR_OUT
- return;
- }
- s^=(d->len&MR_MSBIT);
- if (ld==0)
- {
- if (x->len!=0) x->len|=s;
- MR_OUT
- return;
- }
- for (i=0;iw[ln+i]=d->w[i];
- x->len=(s|(ln+((mr_lentype)ld<ERNUM) return;
- if (mr_notint(x))
- {
- s=(x->len&MR_MSBIT);
- ly=(x->len&MR_OBITS);
- ln=(int)(ly&MR_MSK);
- if (ln==0)
- {
- if(s==MR_MSBIT) convert(_MIPP_ (-1),y);
- else convert(_MIPP_ 1,y);
- return;
- }
- ld=(int)((ly>>MR_BTS)&MR_MSK);
- if (x!=y)
- {
- for (i=0;iw[i]=x->w[i];
- for (i=ln;iw[i]=0;
- }
- else for (i=0;iw[ln+i]=0;
- y->len=(ln|s);
- }
- else copy(x,y);
-}
-
-void denom(_MIPD_ flash x,big y)
-{ /* extract denominator of x */
- int i,ln,ld;
- mr_lentype ly;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
- if (!mr_notint(x))
- {
- convert(_MIPP_ 1,y);
- return;
- }
- ly=(x->len&MR_OBITS);
- ln=(int)(ly&MR_MSK);
- ld=(int)((ly>>MR_BTS)&MR_MSK);
- for (i=0;iw[i]=x->w[ln+i];
- if (x==y) for (i=0;iw[ld+i]=0;
- else for (i=ld;iw[i]=0;
- y->len=ld;
-}
-
-#endif
-
-unsigned int igcd(unsigned int x,unsigned int y)
-{ /* integer GCD, returns GCD of x and y */
- unsigned int r;
- if (y==0) return x;
- while ((r=x%y)!=0)
- x=y,y=r;
- return y;
-}
-
-unsigned long lgcd(unsigned long x,unsigned long y)
-{ /* long GCD, returns GCD of x and y */
- unsigned long r;
- if (y==0) return x;
- while ((r=x%y)!=0)
- x=y,y=r;
- return y;
-}
-
-unsigned int isqrt(unsigned int num,unsigned int guess)
-{ /* square root of an integer */
- unsigned int sqr;
- unsigned int oldguess=guess;
- if (num==0) return 0;
- if (num<4) return 1;
-
- for (;;)
- { /* Newtons iteration */
- /* sqr=guess+(((num/guess)-guess)/2); */
- sqr=((num/guess)+guess)/2;
- if (sqr==guess || sqr==oldguess)
- {
- if (sqr*sqr>num) sqr--;
- return sqr;
- }
- oldguess=guess;
- guess=sqr;
- }
-}
-
-unsigned long mr_lsqrt(unsigned long num,unsigned long guess)
-{ /* square root of a long */
- unsigned long sqr;
- unsigned long oldguess=guess;
- if (num==0) return 0;
- if (num<4) return 1;
-
- for (;;)
- { /* Newtons iteration */
- /* sqr=guess+(((num/guess)-guess)/2); */
- sqr=((num/guess)+guess)/2;
- if (sqr==guess || sqr==oldguess)
- {
- if (sqr*sqr>num) sqr--;
- return sqr;
- }
- oldguess=guess;
- guess=sqr;
- }
-}
-
-mr_small sgcd(mr_small x,mr_small y)
-{ /* integer GCD, returns GCD of x and y */
- mr_small r;
-#ifdef MR_FP
- mr_small dres;
-#endif
- if (y==(mr_small)0) return x;
- while ((r=MR_REMAIN(x,y))!=(mr_small)0)
- x=y,y=r;
- return y;
-}
-
-/* routines to support sliding-windows exponentiation *
- * in various contexts */
-
-int mr_testbit(_MIPD_ big x,int n)
-{ /* return value of n-th bit of big */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-#ifdef MR_FP
- mr_small m,a,dres;
- m=mr_shiftbits((mr_small)1,n%mr_mip->lg2b);
-
- a=x->w[n/mr_mip->lg2b];
-
- a=MR_DIV(a,m);
-
- if ((MR_DIV(a,2.0)*2.0) != a) return 1;
-#else
- if ((x->w[n/mr_mip->lg2b] & ((mr_small)1<<(n%mr_mip->lg2b))) >0) return 1;
-#endif
- return 0;
-}
-
-void mr_addbit(_MIPD_ big x,int n)
-{ /* add 2^n to positive x - where you know that bit is zero. Use with care! */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- mr_lentype m=n/mr_mip->lg2b;
- x->w[m]+=mr_shiftbits((mr_small)1,n%mr_mip->lg2b);
- if (x->lenlen=m+1;
-}
-
-int recode(_MIPD_ big e,int t,int w,int i)
-{ /* recode exponent for Comb method */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- int j,r;
- r=0;
- for (j=w-1;j>=0;j--)
- {
- r<<=1;
- r|=mr_testbit(_MIPP_ e,i+j*t);
- }
- return r;
-}
-
-int mr_window(_MIPD_ big x,int i,int *nbs,int * nzs,int window_size)
-{ /* returns sliding window value, max. of 5 bits, *
- * (Note from version 5.23 this can be changed by *
- * setting parameter window_size. This can be *
- * a useful space-saver) starting at i-th bit of big x. *
- * nbs is number of bits processed, nzs is the number of *
- * additional trailing zeros detected. Returns valid bit *
- * pattern 1x..x1 with no two adjacent 0's. So 10101 *
- * will return 21 with nbs=5, nzs=0. 11001 will return 3,*
- * with nbs=2, nzs=2, having stopped after the first 11..*/
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- int j,r,w;
- w=window_size;
-
-/* check for leading 0 bit */
-
- *nbs=1;
- *nzs=0;
- if (!mr_testbit(_MIPP_ x,i)) return 0;
-
-/* adjust window size if not enough bits left */
-
- if (i-w+1<0) w=i+1;
-
- r=1;
- for (j=i-1;j>i-w;j--)
- { /* accumulate bits. Abort if two 0's in a row */
- (*nbs)++;
- r*=2;
- if (mr_testbit(_MIPP_ x,j)) r+=1;
- if (r%4==0)
- { /* oops - too many zeros - shorten window */
- r/=4;
- *nbs-=2;
- *nzs=2;
- break;
- }
- }
- if (r%2==0)
- { /* remove trailing 0 */
- r/=2;
- *nzs=1;
- (*nbs)--;
- }
- return r;
-}
-
-int mr_window2(_MIPD_ big x,big y,int i,int *nbs,int *nzs)
-{ /* two bit window for double exponentiation */
- int r,w;
- BOOL a,b,c,d;
- w=2;
- *nbs=1;
- *nzs=0;
-
-/* check for two leading 0's */
- a=mr_testbit(_MIPP_ x,i); b=mr_testbit(_MIPP_ y,i);
-
- if (!a && !b) return 0;
- if (i<1) w=1;
-
- if (a)
- {
- if (b) r=3;
- else r=2;
- }
- else r=1;
- if (w==1) return r;
-
- c=mr_testbit(_MIPP_ x,i-1); d=mr_testbit(_MIPP_ y,i-1);
-
- if (!c && !d)
- {
- *nzs=1;
- return r;
- }
-
- *nbs=2;
- r*=4;
- if (c)
- {
- if (d) r+=3;
- else r+=2;
- }
- else r+=1;
- return r;
-}
-
-int mr_naf_window(_MIPD_ big x,big x3,int i,int *nbs,int *nzs,int store)
-{ /* returns sliding window value, using fractional windows *
- * where "store" precomputed values are precalulated and *
- * stored. Scanning starts at the i-th bit of x. nbs is *
- * the number of bits processed. nzs is number of *
- * additional trailing zeros detected. x and x3 (which is *
- * 3*x) are combined to produce the NAF (non-adjacent *
- * form). So if x=11011(27) and x3 is 1010001, the LSB is *
- * ignored and the value 100T0T (32-4-1=27) processed, *
- * where T is -1. Note x.P = (3x-x)/2.P. This value will *
- * return +7, with nbs=4 and nzs=1, having stopped after *
- * the first 4 bits. If it goes too far, it must backtrack *
- * Note in an NAF non-zero elements are never side by side, *
- * so 10T10T won't happen. NOTE: return value n zero or *
- * odd, -21 <= n <= +21 */
-
- int nb,j,r,biggest;
-
- /* get first bit */
- nb=mr_testbit(_MIPP_ x3,i)-mr_testbit(_MIPP_ x,i);
-
- *nbs=1;
- *nzs=0;
- if (nb==0) return 0;
- if (i==0) return nb;
-
- biggest=2*store-1;
-
- if (nb>0) r=1;
- else r=(-1);
-
- for (j=i-1;j>0;j--)
- {
- (*nbs)++;
- r*=2;
- nb=mr_testbit(_MIPP_ x3,j)-mr_testbit(_MIPP_ x,j);
- if (nb>0) r+=1;
- if (nb<0) r-=1;
- if (abs(r)>biggest) break;
- }
-
- if (r%2!=0 && j!=0)
- { /* backtrack */
- if (nb>0) r=(r-1)/2;
- if (nb<0) r=(r+1)/2;
- (*nbs)--;
- }
-
- while (r%2==0)
- { /* remove trailing zeros */
- r/=2;
- (*nzs)++;
- (*nbs)--;
- }
- return r;
-}
-
-/* Some general purpose elliptic curve stuff */
-
-BOOL point_at_infinity(epoint *p)
-{
- if (p==NULL) return FALSE;
- if (p->marker==MR_EPOINT_INFINITY) return TRUE;
- return FALSE;
-}
-
-#ifndef MR_STATIC
-
-epoint* epoint_init(_MIPDO_ )
-{ /* initialise epoint to general point at infinity. */
- epoint *p;
- char *ptr;
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return NULL;
-
- MR_IN(96)
-
-/* Create space for whole structure in one heap access */
-
- p=(epoint *)mr_alloc(_MIPP_ mr_esize(mr_mip->nib-1),1);
-
- ptr=(char *)p+sizeof(epoint);
- p->X=mirvar_mem(_MIPP_ ptr,0);
- p->Y=mirvar_mem(_MIPP_ ptr,1);
-#ifndef MR_AFFINE_ONLY
- p->Z=mirvar_mem(_MIPP_ ptr,2);
-#endif
- p->marker=MR_EPOINT_INFINITY;
-
- MR_OUT
-
- return p;
-}
-
-#endif
-
-epoint* epoint_init_mem_variable(_MIPD_ char *mem,int index,int sz)
-{
- epoint *p;
- char *ptr;
- int offset,r;
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- offset=0;
- r=(unsigned long)mem%MR_SL;
- if (r>0) offset=MR_SL-r;
-
-#ifndef MR_AFFINE_ONLY
- if (mr_mip->coord==MR_AFFINE)
- p=(epoint *)&mem[offset+index*mr_esize_a(sz)];
- else
-#endif
- p=(epoint *)&mem[offset+index*mr_esize(sz)];
-
- ptr=(char *)p+sizeof(epoint);
- p->X=mirvar_mem_variable(ptr,0,sz);
- p->Y=mirvar_mem_variable(ptr,1,sz);
-#ifndef MR_AFFINE_ONLY
- if (mr_mip->coord!=MR_AFFINE) p->Z=mirvar_mem_variable(ptr,2,sz);
-#endif
- p->marker=MR_EPOINT_INFINITY;
- return p;
-}
-
-epoint* epoint_init_mem(_MIPD_ char *mem,int index)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return NULL;
-
- return epoint_init_mem_variable(_MIPP_ mem,index,mr_mip->nib-1);
-}
-
-#ifndef MR_STATIC
-
-/* allocate space for a number of epoints from the heap */
-
-void *ecp_memalloc(_MIPD_ int num)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
-#ifndef MR_AFFINE_ONLY
- if (mr_mip->coord==MR_AFFINE)
- return mr_alloc(_MIPP_ mr_ecp_reserve_a(num,mr_mip->nib-1),1);
- else
-#endif
- return mr_alloc(_MIPP_ mr_ecp_reserve(num,mr_mip->nib-1),1);
-}
-
-#endif
-
-void ecp_memkill(_MIPD_ char *mem,int num)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- if (mem==NULL) return;
-
-#ifndef MR_AFFINE_ONLY
- if (mr_mip->coord==MR_AFFINE)
- memset(mem,0,mr_ecp_reserve_a(num,mr_mip->nib-1));
- else
-#endif
- memset(mem,0,mr_ecp_reserve(num,mr_mip->nib-1));
-
-
-#ifndef MR_STATIC
- mr_free(mem);
-#endif
-}
-
-#ifndef MR_STATIC
-
-void epoint_free(epoint *p)
-{ /* clean up point */
-
- if (p==NULL) return;
- zero(p->X);
- zero(p->Y);
-#ifndef MR_AFFINE_ONLY
- if (p->marker==MR_EPOINT_GENERAL) zero(p->Z);
-#endif
- mr_free(p);
-}
-
-#endif
diff --git a/crypto/sm2/miracl/mrcurve.c b/crypto/sm2/miracl/mrcurve.c
deleted file mode 100644
index 8cfdeb4f..00000000
--- a/crypto/sm2/miracl/mrcurve.c
+++ /dev/null
@@ -1,2507 +0,0 @@
-
-/***************************************************************************
- *
-Copyright 2013 CertiVox IOM Ltd. *
- *
-This file is part of CertiVox MIRACL Crypto SDK. *
- *
-The CertiVox MIRACL Crypto SDK provides developers with an *
-extensive and efficient set of cryptographic functions. *
-For further information about its features and functionalities please *
-refer to http://www.certivox.com *
- *
-* The CertiVox MIRACL Crypto SDK is free software: you can *
- redistribute it and/or modify it under the terms of the *
- GNU Affero General Public License as published by the *
- Free Software Foundation, either version 3 of the License, *
- or (at your option) any later version. *
- *
-* The CertiVox MIRACL Crypto SDK is distributed in the hope *
- that it will be useful, but WITHOUT ANY WARRANTY; without even the *
- implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. *
- See the GNU Affero General Public License for more details. *
- *
-* You should have received a copy of the GNU Affero General Public *
- License along with CertiVox MIRACL Crypto SDK. *
- If not, see . *
- *
-You can be released from the requirements of the license by purchasing *
-a commercial license. Buying such a license is mandatory as soon as you *
-develop commercial activities involving the CertiVox MIRACL Crypto SDK *
-without disclosing the source code of your own applications, or shipping *
-the CertiVox MIRACL Crypto SDK with a closed source product. *
- *
-***************************************************************************/
-/*
- * MIRACL elliptic curve routines
- * mrcurve.c
- *
- * Assumes Weierstrass equation y^2 = x^3 + Ax + B
- * See IEEE P1363 Draft Standard
- *
- * (See below for Edwards coordinates implementation)
- *
- * Uses Montgomery's representation internally
- *
- * Works particularly well with fixed length Comba multiplier
- * e.g. #define MR_COMBA 5 for 5x32 = 160 bit modulus
- * on 32-bit computer
- *
- */
-
-#include
-#include
-#ifdef MR_STATIC
-#include
-#endif
-
-#ifndef MR_EDWARDS
-
-static void epoint_getrhs(_MIPD_ big x,big y)
-{ /* x and y must be different */
-
- /* find x^3+Ax+B */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- nres_modmult(_MIPP_ x,x,y);
-
- nres_modmult(_MIPP_ y,x,y);
- if (mr_abs(mr_mip->Asize)==MR_TOOBIG)
- nres_modmult(_MIPP_ x,mr_mip->A,mr_mip->w1);
- else
- nres_premult(_MIPP_ x,mr_mip->Asize,mr_mip->w1);
- nres_modadd(_MIPP_ y,mr_mip->w1,y);
- if (mr_abs(mr_mip->Bsize)==MR_TOOBIG)
- nres_modadd(_MIPP_ y,mr_mip->B,y);
- else
- {
- convert(_MIPP_ mr_mip->Bsize,mr_mip->w1);
- nres(_MIPP_ mr_mip->w1,mr_mip->w1);
- nres_modadd(_MIPP_ y,mr_mip->w1,y);
- }
-}
-
-#ifndef MR_NOSUPPORT_COMPRESSION
-
-BOOL epoint_x(_MIPD_ big x)
-{ /* test if x is associated with a point on the *
- * currently active curve */
- int j;
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return FALSE;
-
- MR_IN(147)
-
- if (x==NULL) return FALSE;
-
- nres(_MIPP_ x,mr_mip->w2);
- epoint_getrhs(_MIPP_ mr_mip->w2,mr_mip->w3);
-
- if (size(mr_mip->w3)==0)
- {
- MR_OUT
- return TRUE;
- }
-
- redc(_MIPP_ mr_mip->w3,mr_mip->w4);
- j=jack(_MIPP_ mr_mip->w4,mr_mip->modulus);
-
- MR_OUT
- if (j==1) return TRUE;
- return FALSE;
-}
-
-#endif
-
-BOOL epoint_set(_MIPD_ big x,big y,int cb,epoint *p)
-{ /* initialise a point on active ecurve *
- * if x or y == NULL, set to point at infinity *
- * if x==y, a y co-ordinate is calculated - if *
- * possible - and cb suggests LSB 0/1 of y *
- * (which "decompresses" y). Otherwise, check *
- * validity of given (x,y) point, ignoring cb. *
- * Returns TRUE for valid point, otherwise FALSE. */
-
- BOOL valid;
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return FALSE;
-
- MR_IN(97)
-
- if (x==NULL || y==NULL)
- {
- copy(mr_mip->one,p->X);
- copy(mr_mip->one,p->Y);
- p->marker=MR_EPOINT_INFINITY;
- MR_OUT
- return TRUE;
- }
-
-/* find x^3+Ax+B */
-
- nres(_MIPP_ x,p->X);
-
- epoint_getrhs(_MIPP_ p->X,mr_mip->w3);
-
- valid=FALSE;
-
- if (x!=y)
- { /* compare with y^2 */
- nres(_MIPP_ y,p->Y);
- nres_modmult(_MIPP_ p->Y,p->Y,mr_mip->w1);
-
- if (mr_compare(mr_mip->w1,mr_mip->w3)==0) valid=TRUE;
- }
- else
- { /* no y supplied - calculate one. Find square root */
-#ifndef MR_NOSUPPORT_COMPRESSION
-
- valid=nres_sqroot(_MIPP_ mr_mip->w3,p->Y);
- /* check LSB - have we got the right root? */
- redc(_MIPP_ p->Y,mr_mip->w1);
- if (remain(_MIPP_ mr_mip->w1,2)!=cb)
- mr_psub(_MIPP_ mr_mip->modulus,p->Y,p->Y);
-
-#else
- mr_berror(_MIPP_ MR_ERR_NOT_SUPPORTED);
- MR_OUT
- return FALSE;
-#endif
- }
- if (valid)
- {
- p->marker=MR_EPOINT_NORMALIZED;
- MR_OUT
- return TRUE;
- }
-
- MR_OUT
- return FALSE;
-}
-
-#ifndef MR_STATIC
-
-void epoint_getxyz(_MIPD_ epoint *p,big x,big y,big z)
-{ /* get (x,y,z) coordinates */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- MR_IN(143)
- convert(_MIPP_ 1,mr_mip->w1);
- if (p->marker==MR_EPOINT_INFINITY)
- {
-#ifndef MR_AFFINE_ONLY
- if (mr_mip->coord==MR_AFFINE)
- { /* (0,1) or (0,0) = O */
-#endif
- if (x!=NULL) zero(x);
- if (mr_mip->Bsize==0)
- {
- if (y!=NULL) copy(mr_mip->w1,y);
- }
- else
- {
- if (y!=NULL) zero(y);
- }
-#ifndef MR_AFFINE_ONLY
- }
- if (mr_mip->coord==MR_PROJECTIVE)
- { /* (1,1,0) = O */
- if (x!=NULL) copy(mr_mip->w1,x);
- if (y!=NULL) copy(mr_mip->w1,y);
- }
-#endif
- if (z!=NULL) zero(z);
- MR_OUT
- return;
- }
- if (x!=NULL) redc(_MIPP_ p->X,x);
- if (y!=NULL) redc(_MIPP_ p->Y,y);
-#ifndef MR_AFFINE_ONLY
- if (mr_mip->coord==MR_AFFINE)
- {
-#endif
- if (z!=NULL) zero(z);
-#ifndef MR_AFFINE_ONLY
- }
-
- if (mr_mip->coord==MR_PROJECTIVE)
- {
- if (z!=NULL)
- {
- if (p->marker!=MR_EPOINT_GENERAL) copy(mr_mip->w1,z);
- else redc(_MIPP_ p->Z,z);
- }
- }
-#endif
- MR_OUT
- return;
-}
-
-#endif
-
-int epoint_get(_MIPD_ epoint* p,big x,big y)
-{ /* Get point co-ordinates in affine, normal form *
- * (converted from projective, Montgomery form) *
- * if x==y, supplies x only. Return value is Least *
- * Significant Bit of y (useful for point compression) */
-
- int lsb;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- if (p->marker==MR_EPOINT_INFINITY)
- {
- zero(x);
- zero(y);
- return 0;
- }
- if (mr_mip->ERNUM) return 0;
-
- MR_IN(98)
-
- if (!epoint_norm(_MIPP_ p))
- { /* not possible ! */
- MR_OUT
- return (-1);
- }
-
- redc(_MIPP_ p->X,x);
- redc(_MIPP_ p->Y,mr_mip->w1);
-
- if (x!=y) copy(mr_mip->w1,y);
- lsb=remain(_MIPP_ mr_mip->w1,2);
- MR_OUT
- return lsb;
-}
-
-BOOL epoint_norm(_MIPD_ epoint *p)
-{ /* normalise a point */
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
-#ifndef MR_AFFINE_ONLY
-
- if (mr_mip->coord==MR_AFFINE) return TRUE;
- if (p->marker!=MR_EPOINT_GENERAL) return TRUE;
-
- if (mr_mip->ERNUM) return FALSE;
-
- MR_IN(117)
-
- copy(mr_mip->one,mr_mip->w8);
-
- if (nres_moddiv(_MIPP_ mr_mip->w8,p->Z,mr_mip->w8)>1) /* 1/Z */
- {
- epoint_set(_MIPP_ NULL,NULL,0,p);
- mr_berror(_MIPP_ MR_ERR_COMPOSITE_MODULUS);
- MR_OUT
- return FALSE;
- }
-
- nres_modmult(_MIPP_ mr_mip->w8,mr_mip->w8,mr_mip->w1);/* 1/ZZ */
- nres_modmult(_MIPP_ p->X,mr_mip->w1,p->X); /* X/ZZ */
- nres_modmult(_MIPP_ mr_mip->w1,mr_mip->w8,mr_mip->w1);/* 1/ZZZ */
- nres_modmult(_MIPP_ p->Y,mr_mip->w1,p->Y); /* Y/ZZZ */
-
- copy(mr_mip->one,p->Z);
-
- p->marker=MR_EPOINT_NORMALIZED;
- MR_OUT
-
-#endif
-
- return TRUE;
-}
-
-BOOL epoint_multi_norm(_MIPD_ int m,big *work,epoint **p)
-{ /* Normalise an array of points of length mcoord==MR_AFFINE) return TRUE;
- if (mr_mip->ERNUM) return FALSE;
- if (m>MR_MAX_M_T_S) return FALSE;
-
- MR_IN(190)
-
- for (i=0;imarker==MR_EPOINT_NORMALIZED) w[i]=mr_mip->one;
- else w[i]=p[i]->Z;
- if (p[i]->marker==MR_EPOINT_INFINITY) {inf=TRUE; break;} /* whoops, one of them is point at infinity */
- }
-
- if (inf)
- {
- for (i=0;ione,p[i]->Z);
- p[i]->marker=MR_EPOINT_NORMALIZED;
- nres_modmult(_MIPP_ work[i],work[i],mr_mip->w1);
- nres_modmult(_MIPP_ p[i]->X,mr_mip->w1,p[i]->X); /* X/ZZ */
- nres_modmult(_MIPP_ mr_mip->w1,work[i],mr_mip->w1);
- nres_modmult(_MIPP_ p[i]->Y,mr_mip->w1,p[i]->Y); /* Y/ZZZ */
- }
- MR_OUT
-#endif
- return TRUE;
-}
-
-/* adds b+=a, d+=c, and slopes in s1 and s2 */
-
-#ifndef MR_NO_ECC_MULTIADD
-#ifndef MR_STATIC
-
-void ecurve_double_add(_MIPD_ epoint *a,epoint*b,epoint *c,epoint *d,big *s1,big *s2)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(144);
-
-#ifndef MR_AFFINE_ONLY
-
- if (mr_mip->coord==MR_AFFINE)
- {
-#endif
- if (a->marker==MR_EPOINT_INFINITY || size(a->Y)==0)
- {
- *s1=NULL;
- ecurve_add(_MIPP_ c,d);
- *s2=mr_mip->w8;
- MR_OUT
- return;
- }
- if (b->marker==MR_EPOINT_INFINITY || size(b->Y)==0)
- {
- *s1=NULL;
- epoint_copy(a,b);
- ecurve_add(_MIPP_ c,d);
- *s2=mr_mip->w8;
- MR_OUT
- return;
- }
- if (c->marker==MR_EPOINT_INFINITY || size(c->Y)==0)
- {
- ecurve_add(_MIPP_ a,b);
- *s1=mr_mip->w8;
- *s2=NULL;
- MR_OUT
- return;
- }
- if (d->marker==MR_EPOINT_INFINITY || size(d->Y)==0)
- {
- epoint_copy(c,d);
- ecurve_add(_MIPP_ a,b);
- *s1=mr_mip->w8;
- *s2=NULL;
- MR_OUT
- return;
- }
-
- if (a==b || (mr_compare(a->X,b->X)==0 && mr_compare(a->Y,b->Y)==0))
- {
- nres_modmult(_MIPP_ a->X,a->X,mr_mip->w8);
- nres_premult(_MIPP_ mr_mip->w8,3,mr_mip->w8); /* 3x^2 */
- if (mr_abs(mr_mip->Asize)==MR_TOOBIG)
- nres_modadd(_MIPP_ mr_mip->w8,mr_mip->A,mr_mip->w8);
- else
- {
- convert(_MIPP_ mr_mip->Asize,mr_mip->w2);
- nres(_MIPP_ mr_mip->w2,mr_mip->w2);
- nres_modadd(_MIPP_ mr_mip->w8,mr_mip->w2,mr_mip->w8);
- }
- nres_premult(_MIPP_ a->Y,2,mr_mip->w10);
- }
- else
- {
- if (mr_compare(a->X,b->X)==0)
- {
- epoint_set(_MIPP_ NULL,NULL,0,b);
- *s1=NULL;
- ecurve_add(_MIPP_ c,d);
- *s2=mr_mip->w8;
- MR_OUT
- return;
- }
- nres_modsub(_MIPP_ a->Y,b->Y,mr_mip->w8);
- nres_modsub(_MIPP_ a->X,b->X,mr_mip->w10);
- }
-
- if (c==d || (mr_compare(c->X,d->X)==0 && mr_compare(c->Y,d->Y)==0))
- {
- nres_modmult(_MIPP_ c->X,c->X,mr_mip->w9);
- nres_premult(_MIPP_ mr_mip->w9,3,mr_mip->w9); /* 3x^2 */
- if (mr_abs(mr_mip->Asize)==MR_TOOBIG)
- nres_modadd(_MIPP_ mr_mip->w9,mr_mip->A,mr_mip->w9);
- else
- {
- convert(_MIPP_ mr_mip->Asize,mr_mip->w2);
- nres(_MIPP_ mr_mip->w2,mr_mip->w2);
- nres_modadd(_MIPP_ mr_mip->w9,mr_mip->w2,mr_mip->w9);
- }
- nres_premult(_MIPP_ c->Y,2,mr_mip->w11);
- }
- else
- {
- if (mr_compare(c->X,d->X)==0)
- {
- epoint_set(_MIPP_ NULL,NULL,0,d);
- *s2=NULL;
- ecurve_add(_MIPP_ a,b);
- *s1=mr_mip->w8;
- MR_OUT
- return;
- }
- nres_modsub(_MIPP_ c->Y,d->Y,mr_mip->w9);
- nres_modsub(_MIPP_ c->X,d->X,mr_mip->w11);
- }
-
- nres_double_inverse(_MIPP_ mr_mip->w10,mr_mip->w10,mr_mip->w11,mr_mip->w11);
- nres_modmult(_MIPP_ mr_mip->w8,mr_mip->w10,mr_mip->w8);
- nres_modmult(_MIPP_ mr_mip->w9,mr_mip->w11,mr_mip->w9);
-
- nres_modmult(_MIPP_ mr_mip->w8,mr_mip->w8,mr_mip->w2); /* m^2 */
- nres_modsub(_MIPP_ mr_mip->w2,a->X,mr_mip->w1);
- nres_modsub(_MIPP_ mr_mip->w1,b->X,mr_mip->w1);
-
- nres_modsub(_MIPP_ b->X,mr_mip->w1,mr_mip->w2);
- nres_modmult(_MIPP_ mr_mip->w2,mr_mip->w8,mr_mip->w2);
- nres_modsub(_MIPP_ mr_mip->w2,b->Y,b->Y);
- copy(mr_mip->w1,b->X);
- b->marker=MR_EPOINT_GENERAL;
-
- nres_modmult(_MIPP_ mr_mip->w9,mr_mip->w9,mr_mip->w2); /* m^2 */
- nres_modsub(_MIPP_ mr_mip->w2,c->X,mr_mip->w1);
- nres_modsub(_MIPP_ mr_mip->w1,d->X,mr_mip->w1);
-
- nres_modsub(_MIPP_ d->X,mr_mip->w1,mr_mip->w2);
- nres_modmult(_MIPP_ mr_mip->w2,mr_mip->w9,mr_mip->w2);
- nres_modsub(_MIPP_ mr_mip->w2,d->Y,d->Y);
- copy(mr_mip->w1,d->X);
- d->marker=MR_EPOINT_GENERAL;
-
- *s1=mr_mip->w8;
- *s2=mr_mip->w9;
-#ifndef MR_AFFINE_ONLY
- }
- else
- { /* no speed-up */
- ecurve_add(_MIPP_ a,b);
- copy(mr_mip->w8,mr_mip->w9);
- *s1=mr_mip->w9;
- ecurve_add(_MIPP_ c,d);
- *s2=mr_mip->w8;
- }
-#endif
- MR_OUT
-}
-
-void ecurve_multi_add(_MIPD_ int m,epoint **x,epoint**w)
-{ /* adds m points together simultaneously, w[i]+=x[i] */
- int i,*flag;
- big *A,*B,*C;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(122)
-#ifndef MR_AFFINE_ONLY
- if (mr_mip->coord==MR_AFFINE)
- { /* this can be done faster */
-#endif
- A=(big *)mr_alloc(_MIPP_ m,sizeof(big));
- B=(big *)mr_alloc(_MIPP_ m,sizeof(big));
- C=(big *)mr_alloc(_MIPP_ m,sizeof(big));
- flag=(int *)mr_alloc(_MIPP_ m,sizeof(int));
-
- copy(mr_mip->one,mr_mip->w3);
-
- for (i=0;iX,w[i]->X)==0 && mr_compare(x[i]->Y,w[i]->Y)==0)
- { /* doubling */
- if (x[i]->marker==MR_EPOINT_INFINITY || size(x[i]->Y)==0)
- {
- flag[i]=1; /* result is infinity */
- copy(mr_mip->w3,B[i]);
- continue;
- }
- nres_modmult(_MIPP_ x[i]->X,x[i]->X,A[i]);
- nres_premult(_MIPP_ A[i],3,A[i]); /* 3*x^2 */
- if (mr_abs(mr_mip->Asize) == MR_TOOBIG)
- nres_modadd(_MIPP_ A[i],mr_mip->A,A[i]);
- else
- {
- convert(_MIPP_ mr_mip->Asize,mr_mip->w2);
- nres(_MIPP_ mr_mip->w2,mr_mip->w2);
- nres_modadd(_MIPP_ A[i],mr_mip->w2,A[i]);
- } /* 3*x^2+A */
- nres_premult(_MIPP_ x[i]->Y,2,B[i]);
- }
- else
- {
- if (x[i]->marker==MR_EPOINT_INFINITY)
- {
- flag[i]=2; /* w[i] unchanged */
- copy(mr_mip->w3,B[i]);
- continue;
- }
- if (w[i]->marker==MR_EPOINT_INFINITY)
- {
- flag[i]=3; /* w[i] = x[i] */
- copy(mr_mip->w3,B[i]);
- continue;
- }
- nres_modsub(_MIPP_ x[i]->X,w[i]->X,B[i]);
- if (size(B[i])==0)
- { /* point at infinity */
- flag[i]=1; /* result is infinity */
- copy(mr_mip->w3,B[i]);
- continue;
- }
- nres_modsub(_MIPP_ x[i]->Y,w[i]->Y,A[i]);
- }
- }
- nres_multi_inverse(_MIPP_ m,B,C); /* only one inversion needed */
- for (i=0;iw8);
-
- nres_modmult(_MIPP_ mr_mip->w8,mr_mip->w8,mr_mip->w2); /* m^2 */
- nres_modsub(_MIPP_ mr_mip->w2,x[i]->X,mr_mip->w1);
- nres_modsub(_MIPP_ mr_mip->w1,w[i]->X,mr_mip->w1);
-
- nres_modsub(_MIPP_ w[i]->X,mr_mip->w1,mr_mip->w2);
- nres_modmult(_MIPP_ mr_mip->w2,mr_mip->w8,mr_mip->w2);
- nres_modsub(_MIPP_ mr_mip->w2,w[i]->Y,w[i]->Y);
- copy(mr_mip->w1,w[i]->X);
- w[i]->marker=MR_EPOINT_NORMALIZED;
-
- mr_free(C[i]);
- mr_free(B[i]);
- mr_free(A[i]);
- }
- mr_free(flag);
- mr_free(C); mr_free(B); mr_free(A);
-#ifndef MR_AFFINE_ONLY
- }
- else
- { /* no speed-up */
- for (i=0;iERNUM) return;
-
- if (p->marker==MR_EPOINT_INFINITY)
- { /* 2 times infinity == infinity ! */
- return;
- }
-
-#ifndef MR_AFFINE_ONLY
- if (mr_mip->coord==MR_AFFINE)
- { /* 2 sqrs, 1 mul, 1 div */
-#endif
- if (size(p->Y)==0)
- { /* set to point at infinity */
- epoint_set(_MIPP_ NULL,NULL,0,p);
- return;
- }
-
- nres_modmult(_MIPP_ p->X,p->X,mr_mip->w8); /* w8=x^2 */
- nres_premult(_MIPP_ mr_mip->w8,3,mr_mip->w8); /* w8=3*x^2 */
- if (mr_abs(mr_mip->Asize) == MR_TOOBIG)
- nres_modadd(_MIPP_ mr_mip->w8,mr_mip->A,mr_mip->w8);
- else
- {
- convert(_MIPP_ mr_mip->Asize,mr_mip->w2);
- nres(_MIPP_ mr_mip->w2,mr_mip->w2);
- nres_modadd(_MIPP_ mr_mip->w8,mr_mip->w2,mr_mip->w8);
- } /* w8=3*x^2+A */
- nres_premult(_MIPP_ p->Y,2,mr_mip->w6); /* w6=2y */
- if (nres_moddiv(_MIPP_ mr_mip->w8,mr_mip->w6,mr_mip->w8)>1)
- {
- epoint_set(_MIPP_ NULL,NULL,0,p);
- mr_berror(_MIPP_ MR_ERR_COMPOSITE_MODULUS);
- return;
- }
-
-/* w8 is slope m on exit */
-
- nres_modmult(_MIPP_ mr_mip->w8,mr_mip->w8,mr_mip->w2); /* w2=m^2 */
- nres_premult(_MIPP_ p->X,2,mr_mip->w1);
- nres_modsub(_MIPP_ mr_mip->w2,mr_mip->w1,mr_mip->w1); /* w1=m^2-2x */
-
- nres_modsub(_MIPP_ p->X,mr_mip->w1,mr_mip->w2);
- nres_modmult(_MIPP_ mr_mip->w2,mr_mip->w8,mr_mip->w2);
- nres_modsub(_MIPP_ mr_mip->w2,p->Y,p->Y);
- copy(mr_mip->w1,p->X);
-
- return;
-#ifndef MR_AFFINE_ONLY
- }
-
- if (size(p->Y)==0)
- { /* set to point at infinity */
- epoint_set(_MIPP_ NULL,NULL,0,p);
- return;
- }
-
- convert(_MIPP_ 1,mr_mip->w1);
- if (mr_abs(mr_mip->Asize) < MR_TOOBIG)
- {
- if (mr_mip->Asize!=0)
- {
- if (p->marker==MR_EPOINT_NORMALIZED)
- nres(_MIPP_ mr_mip->w1,mr_mip->w6);
- else nres_modmult(_MIPP_ p->Z,p->Z,mr_mip->w6);
- }
-
- if (mr_mip->Asize==(-3))
- { /* a is -3. Goody. 4 sqrs, 4 muls */
- nres_modsub(_MIPP_ p->X,mr_mip->w6,mr_mip->w3);
- nres_modadd(_MIPP_ p->X,mr_mip->w6,mr_mip->w8);
- nres_modmult(_MIPP_ mr_mip->w3,mr_mip->w8,mr_mip->w3);
- nres_modadd(_MIPP_ mr_mip->w3,mr_mip->w3,mr_mip->w8);
- nres_modadd(_MIPP_ mr_mip->w8,mr_mip->w3,mr_mip->w8);
- }
- else
- { /* a is small */
- if (mr_mip->Asize!=0)
- { /* a is non zero! */
- nres_modmult(_MIPP_ mr_mip->w6,mr_mip->w6,mr_mip->w3);
- nres_premult(_MIPP_ mr_mip->w3,mr_mip->Asize,mr_mip->w3);
- }
- nres_modmult(_MIPP_ p->X,p->X,mr_mip->w1);
- nres_modadd(_MIPP_ mr_mip->w1,mr_mip->w1,mr_mip->w8);
- nres_modadd(_MIPP_ mr_mip->w8,mr_mip->w1,mr_mip->w8);
- if (mr_mip->Asize!=0) nres_modadd(_MIPP_ mr_mip->w8,mr_mip->w3,mr_mip->w8);
- }
- }
- else
- { /* a is not special */
- if (p->marker==MR_EPOINT_NORMALIZED) nres(_MIPP_ mr_mip->w1,mr_mip->w6);
- else nres_modmult(_MIPP_ p->Z,p->Z,mr_mip->w6);
-
- nres_modmult(_MIPP_ mr_mip->w6,mr_mip->w6,mr_mip->w3);
- nres_modmult(_MIPP_ mr_mip->w3,mr_mip->A,mr_mip->w3);
- nres_modmult(_MIPP_ p->X,p->X,mr_mip->w1);
- nres_modadd(_MIPP_ mr_mip->w1,mr_mip->w1,mr_mip->w8);
- nres_modadd(_MIPP_ mr_mip->w8,mr_mip->w1,mr_mip->w8);
- nres_modadd(_MIPP_ mr_mip->w8,mr_mip->w3,mr_mip->w8);
- }
-
-/* w8 contains numerator of slope 3x^2+A.z^4 *
- * denominator is now placed in Z */
-
- nres_modmult(_MIPP_ p->Y,p->Y,mr_mip->w2);
- nres_modmult(_MIPP_ p->X,mr_mip->w2,mr_mip->w3);
- nres_modadd(_MIPP_ mr_mip->w3,mr_mip->w3,mr_mip->w3);
- nres_modadd(_MIPP_ mr_mip->w3,mr_mip->w3,mr_mip->w3);
- nres_modmult(_MIPP_ mr_mip->w8,mr_mip->w8,p->X);
- nres_modsub(_MIPP_ p->X,mr_mip->w3,p->X);
- nres_modsub(_MIPP_ p->X,mr_mip->w3,p->X);
-
- if (p->marker==MR_EPOINT_NORMALIZED)
- copy(p->Y,p->Z);
- else nres_modmult(_MIPP_ p->Z,p->Y,p->Z);
- nres_modadd(_MIPP_ p->Z,p->Z,p->Z);
-
- nres_modadd(_MIPP_ mr_mip->w2,mr_mip->w2,mr_mip->w7);
- nres_modmult(_MIPP_ mr_mip->w7,mr_mip->w7,mr_mip->w2);
- nres_modadd(_MIPP_ mr_mip->w2,mr_mip->w2,mr_mip->w2);
- nres_modsub(_MIPP_ mr_mip->w3,p->X,mr_mip->w3);
- nres_modmult(_MIPP_ mr_mip->w8,mr_mip->w3,p->Y);
- nres_modsub(_MIPP_ p->Y,mr_mip->w2,p->Y);
-
-/* alternative method
- nres_modadd(_MIPP_ p->Y,p->Y,mr_mip->w2);
-
- if (p->marker==MR_EPOINT_NORMALIZED)
- copy(mr_mip->w2,p->Z);
-
- else nres_modmult(_MIPP_ mr_mip->w2,p->Z,p->Z);
-
- nres_modmult(_MIPP_ mr_mip->w2,mr_mip->w2,mr_mip->w2);
- nres_modmult(_MIPP_ p->X,mr_mip->w2,mr_mip->w3);
- nres_modadd(_MIPP_ mr_mip->w3,mr_mip->w3,p->X);
- nres_modmult(_MIPP_ mr_mip->w8,mr_mip->w8,mr_mip->w1);
- nres_modsub(_MIPP_ mr_mip->w1,p->X,p->X);
- nres_modmult(_MIPP_ mr_mip->w2,mr_mip->w2,mr_mip->w2);
-
- if (remain(_MIPP_ mr_mip->w2,2)!=0)
- mr_padd(_MIPP_ mr_mip->w2,mr_mip->modulus,mr_mip->w2);
- subdiv(_MIPP_ mr_mip->w2,2,mr_mip->w2);
-
- nres_modsub(_MIPP_ mr_mip->w3,p->X,mr_mip->w3);
- nres_modmult(_MIPP_ mr_mip->w3,mr_mip->w8,mr_mip->w3);
- nres_modsub(_MIPP_ mr_mip->w3,mr_mip->w2,p->Y);
-*/
-
-/*
-
-Observe that when finished w8 contains the line slope, w7 has 2y^2 and w6 has z^2
-This is useful for calculating line functions in pairings
-
-*/
-
- p->marker=MR_EPOINT_GENERAL;
- return;
-#endif
-}
-
-static BOOL ecurve_padd(_MIPD_ epoint *p,epoint *pa)
-{ /* primitive add two epoints on the active ecurve - pa+=p; *
- * note that if p is normalized, its Z coordinate isn't used */
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-#ifndef MR_AFFINE_ONLY
- if (mr_mip->coord==MR_AFFINE)
- { /* 1 sqr, 1 mul, 1 div */
-#endif
- nres_modsub(_MIPP_ p->Y,pa->Y,mr_mip->w8);
- nres_modsub(_MIPP_ p->X,pa->X,mr_mip->w6);
- if (size(mr_mip->w6)==0)
- { /* divide by 0 */
- if (size(mr_mip->w8)==0)
- { /* should have doubled ! */
- return FALSE;
- }
- else
- { /* point at infinity */
- epoint_set(_MIPP_ NULL,NULL,0,pa);
- return TRUE;
- }
- }
- if (nres_moddiv(_MIPP_ mr_mip->w8,mr_mip->w6,mr_mip->w8)>1)
- {
- epoint_set(_MIPP_ NULL,NULL,0,pa);
- mr_berror(_MIPP_ MR_ERR_COMPOSITE_MODULUS);
- return TRUE;
- }
-
- nres_modmult(_MIPP_ mr_mip->w8,mr_mip->w8,mr_mip->w2); /* w2=m^2 */
- nres_modsub(_MIPP_ mr_mip->w2,p->X,mr_mip->w1); /* w1=m^2-x1-x2 */
- nres_modsub(_MIPP_ mr_mip->w1,pa->X,mr_mip->w1);
-
-
- nres_modsub(_MIPP_ pa->X,mr_mip->w1,mr_mip->w2);
- nres_modmult(_MIPP_ mr_mip->w2,mr_mip->w8,mr_mip->w2);
- nres_modsub(_MIPP_ mr_mip->w2,pa->Y,pa->Y);
- copy(mr_mip->w1,pa->X);
-
- pa->marker=MR_EPOINT_NORMALIZED;
- return TRUE;
-#ifndef MR_AFFINE_ONLY
- }
-
- if (p->marker!=MR_EPOINT_NORMALIZED)
- {
- nres_modmult(_MIPP_ p->Z,p->Z,mr_mip->w6);
- nres_modmult(_MIPP_ pa->X,mr_mip->w6,mr_mip->w1);
- nres_modmult(_MIPP_ mr_mip->w6,p->Z,mr_mip->w6);
- nres_modmult(_MIPP_ pa->Y,mr_mip->w6,mr_mip->w8);
- }
- else
- {
- copy(pa->X,mr_mip->w1);
- copy(pa->Y,mr_mip->w8);
- }
- if (pa->marker==MR_EPOINT_NORMALIZED)
- copy(mr_mip->one,mr_mip->w6);
-
- else nres_modmult(_MIPP_ pa->Z,pa->Z,mr_mip->w6);
- nres_modmult(_MIPP_ p->X,mr_mip->w6,mr_mip->w4);
- if (pa->marker!=MR_EPOINT_NORMALIZED)
- nres_modmult(_MIPP_ mr_mip->w6,pa->Z,mr_mip->w6);
- nres_modmult(_MIPP_ p->Y,mr_mip->w6,mr_mip->w5);
- nres_modsub(_MIPP_ mr_mip->w1,mr_mip->w4,mr_mip->w1);
- nres_modsub(_MIPP_ mr_mip->w8,mr_mip->w5,mr_mip->w8);
-
-/* w8 contains the numerator of the slope */
-
- if (size(mr_mip->w1)==0)
- {
- if (size(mr_mip->w8)==0)
- { /* should have doubled ! */
- return FALSE;
- }
- else
- { /* point at infinity */
- epoint_set(_MIPP_ NULL,NULL,0,pa);
- return TRUE;
- }
- }
- nres_modadd(_MIPP_ mr_mip->w4,mr_mip->w4,mr_mip->w6);
- nres_modadd(_MIPP_ mr_mip->w1,mr_mip->w6,mr_mip->w4);
- nres_modadd(_MIPP_ mr_mip->w5,mr_mip->w5,mr_mip->w6);
- nres_modadd(_MIPP_ mr_mip->w8,mr_mip->w6,mr_mip->w5);
-
- if (p->marker!=MR_EPOINT_NORMALIZED)
- {
- if (pa->marker!=MR_EPOINT_NORMALIZED)
- nres_modmult(_MIPP_ pa->Z,p->Z,mr_mip->w3);
- else
- copy(p->Z,mr_mip->w3);
- nres_modmult(_MIPP_ mr_mip->w3,mr_mip->w1,pa->Z);
- }
- else
- {
- if (pa->marker!=MR_EPOINT_NORMALIZED)
- nres_modmult(_MIPP_ pa->Z,mr_mip->w1,pa->Z);
- else
- copy(mr_mip->w1,pa->Z);
- }
- nres_modmult(_MIPP_ mr_mip->w1,mr_mip->w1,mr_mip->w6);
- nres_modmult(_MIPP_ mr_mip->w1,mr_mip->w6,mr_mip->w1);
- nres_modmult(_MIPP_ mr_mip->w6,mr_mip->w4,mr_mip->w6);
- nres_modmult(_MIPP_ mr_mip->w8,mr_mip->w8,mr_mip->w4);
-
- nres_modsub(_MIPP_ mr_mip->w4,mr_mip->w6,pa->X);
- nres_modsub(_MIPP_ mr_mip->w6,pa->X,mr_mip->w6);
- nres_modsub(_MIPP_ mr_mip->w6,pa->X,mr_mip->w6);
- nres_modmult(_MIPP_ mr_mip->w8,mr_mip->w6,mr_mip->w2);
- nres_modmult(_MIPP_ mr_mip->w1,mr_mip->w5,mr_mip->w1);
- nres_modsub(_MIPP_ mr_mip->w2,mr_mip->w1,mr_mip->w5);
-
-/* divide by 2 */
-
- nres_div2(_MIPP_ mr_mip->w5,pa->Y);
-
- pa->marker=MR_EPOINT_GENERAL;
- return TRUE;
-#endif
-}
-
-void epoint_copy(epoint *a,epoint *b)
-{
- if (a==b || b==NULL) return;
-
- copy(a->X,b->X);
- copy(a->Y,b->Y);
-#ifndef MR_AFFINE_ONLY
- if (a->marker==MR_EPOINT_GENERAL) copy(a->Z,b->Z);
-#endif
- b->marker=a->marker;
- return;
-}
-
-BOOL epoint_comp(_MIPD_ epoint *a,epoint *b)
-{
- BOOL result;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return FALSE;
- if (a==b) return TRUE;
- if (a->marker==MR_EPOINT_INFINITY)
- {
- if (b->marker==MR_EPOINT_INFINITY) return TRUE;
- else return FALSE;
- }
- if (b->marker==MR_EPOINT_INFINITY)
- return FALSE;
-
-#ifndef MR_AFFINE_ONLY
- if (mr_mip->coord==MR_AFFINE)
- {
-#endif
- if (mr_compare(a->X,b->X)==0 && mr_compare(a->Y,b->Y)==0) result=TRUE;
- else result=FALSE;
- return result;
-#ifndef MR_AFFINE_ONLY
- }
-
- if (mr_mip->coord==MR_PROJECTIVE)
- {
- MR_IN(105)
- if (a->marker!=MR_EPOINT_GENERAL)
- copy(mr_mip->one,mr_mip->w1);
- else copy(a->Z,mr_mip->w1);
-
- if (b->marker!=MR_EPOINT_GENERAL)
- copy(mr_mip->one,mr_mip->w2);
- else copy(b->Z,mr_mip->w2);
-
- nres_modmult(_MIPP_ mr_mip->w1,mr_mip->w1,mr_mip->w3); /* Za*Za */
- nres_modmult(_MIPP_ mr_mip->w2,mr_mip->w2,mr_mip->w4); /* Zb*Zb */
-
- nres_modmult(_MIPP_ a->X,mr_mip->w4,mr_mip->w5); /* Xa*Zb*Zb */
- nres_modmult(_MIPP_ b->X,mr_mip->w3,mr_mip->w6); /* Xb*Za*Za */
-
- if (mr_compare(mr_mip->w5,mr_mip->w6)!=0) result=FALSE;
- else
- {
- nres_modmult(_MIPP_ mr_mip->w1,mr_mip->w3,mr_mip->w3);
- nres_modmult(_MIPP_ mr_mip->w2,mr_mip->w4,mr_mip->w4);
-
- nres_modmult(_MIPP_ a->Y,mr_mip->w4,mr_mip->w5);
- nres_modmult(_MIPP_ b->Y,mr_mip->w3,mr_mip->w6);
-
- if (mr_compare(mr_mip->w5,mr_mip->w6)!=0) result=FALSE;
- else result=TRUE;
- }
- MR_OUT
- return result;
- }
- return FALSE;
-#endif
-}
-
-int ecurve_add(_MIPD_ epoint *p,epoint *pa)
-{ /* pa=pa+p; */
- /* An ephemeral pointer to the line slope is returned */
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return MR_OVER;
-
- MR_IN(94)
-
- if (p==pa)
- {
- ecurve_double(_MIPP_ pa);
- MR_OUT
- if (pa->marker==MR_EPOINT_INFINITY) return MR_OVER;
- return MR_DOUBLE;
- }
- if (pa->marker==MR_EPOINT_INFINITY)
- {
- epoint_copy(p,pa);
- MR_OUT
- return MR_ADD;
- }
- if (p->marker==MR_EPOINT_INFINITY)
- {
- MR_OUT
- return MR_ADD;
- }
-
- if (!ecurve_padd(_MIPP_ p,pa))
- {
- ecurve_double(_MIPP_ pa);
- MR_OUT
- return MR_DOUBLE;
- }
- MR_OUT
- if (pa->marker==MR_EPOINT_INFINITY) return MR_OVER;
- return MR_ADD;
-}
-
-void epoint_negate(_MIPD_ epoint *p)
-{ /* negate a point */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
- if (p->marker==MR_EPOINT_INFINITY) return;
-
- MR_IN(121)
- if (size(p->Y)!=0) mr_psub(_MIPP_ mr_mip->modulus,p->Y,p->Y);
- MR_OUT
-}
-
-int ecurve_sub(_MIPD_ epoint *p,epoint *pa)
-{
- int r;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return MR_OVER;
-
- MR_IN(104)
-
- if (p==pa)
- {
- epoint_set(_MIPP_ NULL,NULL,0,pa);
- MR_OUT
- return MR_OVER;
- }
- if (p->marker==MR_EPOINT_INFINITY)
- {
- MR_OUT
- return MR_ADD;
- }
-
- epoint_negate(_MIPP_ p);
- r=ecurve_add(_MIPP_ p,pa);
- epoint_negate(_MIPP_ p);
-
- MR_OUT
- return r;
-}
-
-int ecurve_mult(_MIPD_ big e,epoint *pa,epoint *pt)
-{ /* pt=e*pa; */
- int i,j,n,nb,nbs,nzs,nadds;
- epoint *table[MR_ECC_STORE_N];
-#ifndef MR_AFFINE_ONLY
- big work[MR_ECC_STORE_N];
-#endif
-
-#ifdef MR_STATIC
- char mem[MR_ECP_RESERVE(MR_ECC_STORE_N)];
-#ifndef MR_AFFINE_ONLY
- char mem1[MR_BIG_RESERVE(MR_ECC_STORE_N)];
-#endif
-#else
- char *mem;
-#ifndef MR_AFFINE_ONLY
- char *mem1;
-#endif
-#endif
-
-#ifndef MR_ALWAYS_BINARY
- epoint *p;
- int ce,ch;
-#endif
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return 0;
-
- MR_IN(95)
- if (size(e)==0)
- { /* multiplied by 0 */
- epoint_set(_MIPP_ NULL,NULL,0,pt);
- MR_OUT
- return 0;
- }
- copy(e,mr_mip->w9);
-/* epoint_norm(_MIPP_ pa); */
- epoint_copy(pa,pt);
-
- if (size(mr_mip->w9)<0)
- { /* pt = -pt */
- negify(mr_mip->w9,mr_mip->w9);
- epoint_negate(_MIPP_ pt);
- }
-
- if (size(mr_mip->w9)==1)
- {
- MR_OUT
- return 0;
- }
-
- premult(_MIPP_ mr_mip->w9,3,mr_mip->w10); /* h=3*e */
-
-#ifndef MR_STATIC
-#ifndef MR_ALWAYS_BINARY
- if (mr_mip->base==mr_mip->base2)
- {
-#endif
-#endif
-
-#ifdef MR_STATIC
- memset(mem,0,MR_ECP_RESERVE(MR_ECC_STORE_N));
-#ifndef MR_AFFINE_ONLY
- memset(mem1,0,MR_BIG_RESERVE(MR_ECC_STORE_N));
-#endif
-#else
- mem=(char *)ecp_memalloc(_MIPP_ MR_ECC_STORE_N);
-#ifndef MR_AFFINE_ONLY
- mem1=(char *)memalloc(_MIPP_ MR_ECC_STORE_N);
-#endif
-#endif
-
- for (i=0;i<=MR_ECC_STORE_N-1;i++)
- {
- table[i]=epoint_init_mem(_MIPP_ mem,i);
-#ifndef MR_AFFINE_ONLY
- work[i]=mirvar_mem(_MIPP_ mem1,i);
-#endif
- }
-
- epoint_copy(pt,table[0]);
- epoint_copy(table[0],table[MR_ECC_STORE_N-1]);
- ecurve_double(_MIPP_ table[MR_ECC_STORE_N-1]);
- /* epoint_norm(_MIPP_ table[MR_ECC_STORE_N-1]); */
-
- for (i=1;iw10);
- nadds=0;
- epoint_set(_MIPP_ NULL,NULL,0,pt);
- for (i=nb-1;i>=1;)
- { /* add/subtract */
- if (mr_mip->user!=NULL) (*mr_mip->user)();
- n=mr_naf_window(_MIPP_ mr_mip->w9,mr_mip->w10,i,&nbs,&nzs,MR_ECC_STORE_N);
- for (j=0;j0) {ecurve_add(_MIPP_ table[n/2],pt); nadds++;}
- if (n<0) {ecurve_sub(_MIPP_ table[(-n)/2],pt); nadds++;}
- i-=nbs;
- if (nzs)
- {
- for (j=0;jw10)-1,mr_mip->w11);
- mr_psub(_MIPP_ mr_mip->w10,mr_mip->w11,mr_mip->w10);
- subdiv(_MIPP_ mr_mip->w11,2,mr_mip->w11);
- while (size(mr_mip->w11) > 1)
- { /* add/subtract method */
- if (mr_mip->user!=NULL) (*mr_mip->user)();
-
- ecurve_double(_MIPP_ pt);
- ce=mr_compare(mr_mip->w9,mr_mip->w11); /* e(i)=1? */
- ch=mr_compare(mr_mip->w10,mr_mip->w11); /* h(i)=1? */
- if (ch>=0)
- { /* h(i)=1 */
- if (ce<0) {ecurve_add(_MIPP_ p,pt); nadds++;}
- mr_psub(_MIPP_ mr_mip->w10,mr_mip->w11,mr_mip->w10);
- }
- if (ce>=0)
- { /* e(i)=1 */
- if (ch<0) {ecurve_sub(_MIPP_ p,pt); nadds++;}
- mr_psub(_MIPP_ mr_mip->w9,mr_mip->w11,mr_mip->w9);
- }
- subdiv(_MIPP_ mr_mip->w11,2,mr_mip->w11);
- }
- ecp_memkill(_MIPP_ mem,1);
- }
-#endif
-#endif
- MR_OUT
- return nadds;
-}
-
-#ifndef MR_NO_ECC_MULTIADD
-#ifndef MR_STATIC
-
-void ecurve_multn(_MIPD_ int n,big *y,epoint **x,epoint *w)
-{ /* pt=e[o]*p[0]+e[1]*p[1]+ .... e[n-1]*p[n-1] */
- int i,j,k,m,nb,ea;
- epoint **G;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(114)
-
- m=1< nb) nb=k;
-
- epoint_set(_MIPP_ NULL,NULL,0,w); /* w=0 */
-
-#ifndef MR_ALWAYS_BINARY
- if (mr_mip->base==mr_mip->base2)
- {
-#endif
- for (i=nb-1;i>=0;i--)
- {
- if (mr_mip->user!=NULL) (*mr_mip->user)();
- ea=0;
- k=1;
- for (j=0;jERNUM) return FALSE;
-
- if (P->marker==MR_EPOINT_GENERAL || Q->marker==MR_EPOINT_GENERAL)
- {
- mr_berror(_MIPP_ MR_ERR_BAD_PARAMETERS);
- MR_OUT
- return FALSE;
- }
-
- if (mr_compare(P->X,Q->X)==0)
- { /* P=Q or P=-Q - shouldn't happen */
- epoint_copy(P,PP);
- ecurve_add(_MIPP_ Q,PP);
- epoint_copy(P,PM);
- ecurve_sub(_MIPP_ Q,PM);
-
- MR_OUT
- return TRUE;
- }
-
- t1= mr_mip->w10;
- t2= mr_mip->w11;
- lam = mr_mip->w13;
-
- copy(P->X,t2);
- nres_modsub(_MIPP_ t2,Q->X,t2);
-
- redc(_MIPP_ t2,t2);
- invmodp(_MIPP_ t2,mr_mip->modulus,t2);
- nres(_MIPP_ t2,t2);
-
- nres_modadd(_MIPP_ P->X,Q->X,PP->X);
- copy(PP->X,PM->X);
-
- copy(P->Y,t1);
- nres_modsub(_MIPP_ t1,Q->Y,t1);
- copy(t1,lam);
- nres_modmult(_MIPP_ lam,t2,lam);
- copy(lam,t1);
- nres_modmult(_MIPP_ t1,t1,t1);
- nres_modsub(_MIPP_ t1,PP->X,PP->X);
- copy(Q->X,PP->Y);
- nres_modsub(_MIPP_ PP->Y,PP->X,PP->Y);
- nres_modmult(_MIPP_ PP->Y,lam,PP->Y);
- nres_modsub(_MIPP_ PP->Y,Q->Y,PP->Y);
-
- copy(P->Y,t1);
- nres_modadd(_MIPP_ t1,Q->Y,t1);
- copy(t1,lam);
- nres_modmult(_MIPP_ lam,t2,lam);
- copy(lam,t1);
- nres_modmult(_MIPP_ t1,t1,t1);
- nres_modsub(_MIPP_ t1,PM->X,PM->X);
- copy(Q->X,PM->Y);
- nres_modsub(_MIPP_ PM->Y,PM->X,PM->Y);
- nres_modmult(_MIPP_ PM->Y,lam,PM->Y);
- nres_modadd(_MIPP_ PM->Y,Q->Y,PM->Y);
-
- PP->marker=MR_EPOINT_NORMALIZED;
- PM->marker=MR_EPOINT_NORMALIZED;
-
- return TRUE;
-}
-
-void ecurve_mult2(_MIPD_ big e,epoint *p,big ea,epoint *pa,epoint *pt)
-{ /* pt=e*p+ea*pa; */
- int e1,h1,e2,h2,bb;
- epoint *p1,*p2,*ps[2];
-#ifdef MR_STATIC
- char mem[MR_ECP_RESERVE(4)];
-#else
- char *mem;
-#endif
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- if (mr_mip->ERNUM) return;
-
- MR_IN(103)
-
- if (size(e)==0)
- {
- ecurve_mult(_MIPP_ ea,pa,pt);
- MR_OUT
- return;
- }
-#ifdef MR_STATIC
- memset(mem,0,MR_ECP_RESERVE(4));
-#else
- mem=(char *)ecp_memalloc(_MIPP_ 4);
-#endif
- p2=epoint_init_mem(_MIPP_ mem,0);
- p1=epoint_init_mem(_MIPP_ mem,1);
- ps[0]=epoint_init_mem(_MIPP_ mem,2);
- ps[1]=epoint_init_mem(_MIPP_ mem,3);
-
- epoint_norm(_MIPP_ pa);
- epoint_copy(pa,p2);
- copy(ea,mr_mip->w9);
- if (size(mr_mip->w9)<0)
- { /* p2 = -p2 */
- negify(mr_mip->w9,mr_mip->w9);
- epoint_negate(_MIPP_ p2);
- }
-
- epoint_norm(_MIPP_ p);
- epoint_copy(p,p1);
- copy(e,mr_mip->w12);
- if (size(mr_mip->w12)<0)
- { /* p1= -p1 */
- negify(mr_mip->w12,mr_mip->w12);
- epoint_negate(_MIPP_ p1);
- }
-
-
- epoint_set(_MIPP_ NULL,NULL,0,pt); /* pt=0 */
- ecurve_add_sub(_MIPP_ p1,p2,ps[0],ps[1]); /* only one inversion! ps[0]=p1+p2, ps[1]=p1-p2 */
-
- mr_jsf(_MIPP_ mr_mip->w9,mr_mip->w12,mr_mip->w10,mr_mip->w9,mr_mip->w13,mr_mip->w12);
-
-/* To use a simple NAF instead, substitute this for the JSF
- premult(_MIPP_ mr_mip->w9,3,mr_mip->w10); 3*ea
- premult(_MIPP_ mr_mip->w12,3,mr_mip->w13); 3*e
-*/
-
-#ifndef MR_ALWAYS_BINARY
- if (mr_mip->base==mr_mip->base2)
- {
-#endif
- if (mr_compare(mr_mip->w10,mr_mip->w13)>=0) bb=logb2(_MIPP_ mr_mip->w10)-1;
- else bb=logb2(_MIPP_ mr_mip->w13)-1;
-
- while (bb>=0) /* for the simple NAF, this should be 1 */
- {
- if (mr_mip->user!=NULL) (*mr_mip->user)();
- ecurve_double(_MIPP_ pt);
-
- e1=h1=e2=h2=0;
- if (mr_testbit(_MIPP_ mr_mip->w9,bb)) e2=1;
- if (mr_testbit(_MIPP_ mr_mip->w10,bb)) h2=1;
- if (mr_testbit(_MIPP_ mr_mip->w12,bb)) e1=1;
- if (mr_testbit(_MIPP_ mr_mip->w13,bb)) h1=1;
-
- if (e1!=h1)
- {
- if (e2==h2)
- {
- if (h1==1) ecurve_add(_MIPP_ p1,pt);
- else ecurve_sub(_MIPP_ p1,pt);
- }
- else
- {
- if (h1==1)
- {
- if (h2==1) ecurve_add(_MIPP_ ps[0],pt);
- else ecurve_add(_MIPP_ ps[1],pt);
- }
- else
- {
- if (h2==1) ecurve_sub(_MIPP_ ps[1],pt);
- else ecurve_sub(_MIPP_ ps[0],pt);
- }
- }
- }
- else if (e2!=h2)
- {
- if (h2==1) ecurve_add(_MIPP_ p2,pt);
- else ecurve_sub(_MIPP_ p2,pt);
- }
- bb-=1;
- }
-#ifndef MR_ALWAYS_BINARY
- }
- else
- {
- if (mr_compare(mr_mip->w10,mr_mip->w13)>=0)
- expb2(_MIPP_ logb2(_MIPP_ mr_mip->w10)-1,mr_mip->w11);
- else expb2(_MIPP_ logb2(_MIPP_ mr_mip->w13)-1,mr_mip->w11);
-
- while (size(mr_mip->w11) > 0) /* for the NAF, this should be 1 */
- { /* add/subtract method */
- if (mr_mip->user!=NULL) (*mr_mip->user)();
-
- ecurve_double(_MIPP_ pt);
-
- e1=h1=e2=h2=0;
- if (mr_compare(mr_mip->w9,mr_mip->w11)>=0)
- { /* e1(i)=1? */
- e2=1;
- mr_psub(_MIPP_ mr_mip->w9,mr_mip->w11,mr_mip->w9);
- }
- if (mr_compare(mr_mip->w10,mr_mip->w11)>=0)
- { /* h1(i)=1? */
- h2=1;
- mr_psub(_MIPP_ mr_mip->w10,mr_mip->w11,mr_mip->w10);
- }
- if (mr_compare(mr_mip->w12,mr_mip->w11)>=0)
- { /* e2(i)=1? */
- e1=1;
- mr_psub(_MIPP_ mr_mip->w12,mr_mip->w11,mr_mip->w12);
- }
- if (mr_compare(mr_mip->w13,mr_mip->w11)>=0)
- { /* h2(i)=1? */
- h1=1;
- mr_psub(_MIPP_ mr_mip->w13,mr_mip->w11,mr_mip->w13);
- }
-
- if (e1!=h1)
- {
- if (e2==h2)
- {
- if (h1==1) ecurve_add(_MIPP_ p1,pt);
- else ecurve_sub(_MIPP_ p1,pt);
- }
- else
- {
- if (h1==1)
- {
- if (h2==1) ecurve_add(_MIPP_ ps[0],pt);
- else ecurve_add(_MIPP_ ps[1],pt);
- }
- else
- {
- if (h2==1) ecurve_sub(_MIPP_ ps[1],pt);
- else ecurve_sub(_MIPP_ ps[0],pt);
- }
- }
- }
- else if (e2!=h2)
- {
- if (h2==1) ecurve_add(_MIPP_ p2,pt);
- else ecurve_sub(_MIPP_ p2,pt);
- }
-
- subdiv(_MIPP_ mr_mip->w11,2,mr_mip->w11);
- }
- }
-#endif
- ecp_memkill(_MIPP_ mem,4);
- MR_OUT
-}
-
-#endif
-
-#else
-
-/* Twisted Inverted Edwards curves
-
- * Assumes Twisted Inverted Edward's equation x^2+Ay^2 = x^2.y^2 + B
- * Assumes points are not of order 2 or 4
-*/
-
-static void epoint_getrhs(_MIPD_ big x,big y)
-{
- /* find RHS=(x^2-B)/(x^2-A) */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- nres_modmult(_MIPP_ x,x,mr_mip->w6);
- nres_modsub(_MIPP_ mr_mip->w6,mr_mip->B,y);
- nres_modsub(_MIPP_ mr_mip->w6,mr_mip->A,mr_mip->w6);
-
- nres_moddiv(_MIPP_ y,mr_mip->w6,y);
-}
-
-#ifndef MR_NOSUPPORT_COMPRESSION
-
-BOOL epoint_x(_MIPD_ big x)
-{ /* test if x is associated with a point on the *
- * currently active curve */
- int j;
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return FALSE;
-
- MR_IN(147)
-
- if (x==NULL) return FALSE;
-
- nres(_MIPP_ x,mr_mip->w2);
- epoint_getrhs(_MIPP_ mr_mip->w2,mr_mip->w7);
-
- if (size(mr_mip->w7)==0)
- {
- MR_OUT
- return TRUE;
- }
-
- redc(_MIPP_ mr_mip->w7,mr_mip->w4);
- j=jack(_MIPP_ mr_mip->w4,mr_mip->modulus);
-
- MR_OUT
- if (j==1) return TRUE;
- return FALSE;
-}
-
-#endif
-
-BOOL epoint_set(_MIPD_ big x,big y,int cb,epoint *p)
-{ /* initialise a point on active ecurve *
- * if x or y == NULL, set to point at infinity *
- * if x==y, a y co-ordinate is calculated - if *
- * possible - and cb suggests LSB 0/1 of y *
- * (which "decompresses" y). Otherwise, check *
- * validity of given (x,y) point, ignoring cb. *
- * Returns TRUE for valid point, otherwise FALSE. */
-
- BOOL valid;
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return FALSE;
-
- MR_IN(97)
-
- if (x==NULL || y==NULL)
- {
- copy(mr_mip->one,p->X);
- zero(p->Y);
- p->marker=MR_EPOINT_INFINITY;
- MR_OUT
- return TRUE;
- }
-
- valid=FALSE;
- nres(_MIPP_ x,p->X);
- if (x!=y)
- { /* Check directly that x^2+Ay^2 == x^2.y^2+B */
- nres(_MIPP_ y,p->Y);
- nres_modmult(_MIPP_ p->X,p->X,mr_mip->w1);
- nres_modmult(_MIPP_ p->Y,p->Y,mr_mip->w2);
- nres_modmult(_MIPP_ mr_mip->w1,mr_mip->w2,mr_mip->w3);
- nres_modadd(_MIPP_ mr_mip->w3,mr_mip->B,mr_mip->w3);
-
-
- if (mr_abs(mr_mip->Asize)==MR_TOOBIG)
- nres_modmult(_MIPP_ mr_mip->w2,mr_mip->A,mr_mip->w2);
- else
- nres_premult(_MIPP_ mr_mip->w2,mr_mip->Asize,mr_mip->w2);
- nres_modadd(_MIPP_ mr_mip->w2,mr_mip->w1,mr_mip->w2);
- if (mr_compare(mr_mip->w2,mr_mip->w3)==0) valid=TRUE;
- }
- else
- { /* find RHS */
- epoint_getrhs(_MIPP_ p->X,mr_mip->w7);
- /* no y supplied - calculate one. Find square root */
-#ifndef MR_NOSUPPORT_COMPRESSION
- valid=nres_sqroot(_MIPP_ mr_mip->w7,p->Y);
- /* check LSB - have we got the right root? */
- redc(_MIPP_ p->Y,mr_mip->w1);
- if (remain(_MIPP_ mr_mip->w1,2)!=cb)
- mr_psub(_MIPP_ mr_mip->modulus,p->Y,p->Y);
-
-#else
- mr_berror(_MIPP_ MR_ERR_NOT_SUPPORTED);
- MR_OUT
- return FALSE;
-#endif
- }
- if (valid)
- {
- p->marker=MR_EPOINT_NORMALIZED;
- MR_OUT
- return TRUE;
- }
-
- MR_OUT
- return FALSE;
-}
-
-#ifndef MR_STATIC
-
-void epoint_getxyz(_MIPD_ epoint *p,big x,big y,big z)
-{ /* get (x,y,z) coordinates */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- MR_IN(143)
- convert(_MIPP_ 1,mr_mip->w1);
- if (p->marker==MR_EPOINT_INFINITY)
- {
- if (x!=NULL) copy(mr_mip->w1,x);
- if (y!=NULL) zero(y);
- if (z!=NULL) zero(z);
- MR_OUT
- return;
- }
- if (x!=NULL) redc(_MIPP_ p->X,x);
- if (y!=NULL) redc(_MIPP_ p->Y,y);
- if (z!=NULL) redc(_MIPP_ p->Z,z);
-
- MR_OUT
- return;
-}
-
-#endif
-
-int epoint_get(_MIPD_ epoint* p,big x,big y)
-{ /* Get point co-ordinates in affine, normal form *
- * (converted from projective, Montgomery form) *
- * if x==y, supplies x only. Return value is Least *
- * Significant Bit of y (useful for point compression) */
-
- int lsb;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- if (p->marker==MR_EPOINT_INFINITY)
- {
- zero(y);
- convert(_MIPP_ 1,x);
- return 0;
- }
- if (mr_mip->ERNUM) return 0;
-
- MR_IN(98)
-
- if (!epoint_norm(_MIPP_ p))
- { /* not possible ! */
- MR_OUT
- return (-1);
- }
-
- redc(_MIPP_ p->X,x);
- redc(_MIPP_ p->Y,mr_mip->w1);
-
- if (x!=y) copy(mr_mip->w1,y);
- lsb=remain(_MIPP_ mr_mip->w1,2);
- MR_OUT
- return lsb;
-}
-
-BOOL epoint_norm(_MIPD_ epoint *p)
-{ /* normalise a point */
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- if (p->marker!=MR_EPOINT_GENERAL) return TRUE;
-
- if (mr_mip->ERNUM) return FALSE;
-
- MR_IN(117)
-
- copy(mr_mip->one,mr_mip->w8);
-
- if (nres_moddiv(_MIPP_ mr_mip->w8,p->Z,mr_mip->w8)>1) /* 1/Z */
- {
- epoint_set(_MIPP_ NULL,NULL,0,p);
- mr_berror(_MIPP_ MR_ERR_COMPOSITE_MODULUS);
- MR_OUT
- return FALSE;
- }
-
- nres_modmult(_MIPP_ p->X,mr_mip->w8,p->X); /* X/Z */
- nres_modmult(_MIPP_ p->Y,mr_mip->w8,p->Y); /* Y/Z */
-
- copy(mr_mip->one,p->Z);
-
- p->marker=MR_EPOINT_NORMALIZED;
- MR_OUT
-
- return TRUE;
-}
-
-void ecurve_double(_MIPD_ epoint *p)
-{ /* double epoint on active ecurve */
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- if (p->marker==MR_EPOINT_INFINITY)
- { /* 2 times infinity == infinity ! */
- return;
- }
- nres_modadd(_MIPP_ p->X,p->Y,mr_mip->w1);
-
- nres_modmult(_MIPP_ p->X,p->X,p->X); /* A=X1^2 */
- nres_modmult(_MIPP_ p->Y,p->Y,p->Y); /* B=Y1^2 */
- nres_modmult(_MIPP_ mr_mip->w1,mr_mip->w1,mr_mip->w1); /* (X+Y)^2 */
- nres_modsub(_MIPP_ mr_mip->w1,p->X,mr_mip->w1);
- nres_modsub(_MIPP_ mr_mip->w1,p->Y,mr_mip->w1); /* E=(X+Y)^2-A-B */
-
- if (mr_abs(mr_mip->Asize)==MR_TOOBIG) /* U = aB */
- nres_modmult(_MIPP_ p->Y,mr_mip->A,p->Y);
- else
- nres_premult(_MIPP_ p->Y,mr_mip->Asize,p->Y);
-
- if (p->marker!=MR_EPOINT_NORMALIZED)
- nres_modmult(_MIPP_ p->Z,p->Z,p->Z);
- else
- copy(mr_mip->one,p->Z);
-
- nres_modadd(_MIPP_ p->Z,p->Z,p->Z);
- if (mr_abs(mr_mip->Bsize)==MR_TOOBIG) /* 2dZ^2 */
- nres_modmult(_MIPP_ p->Z,mr_mip->B,p->Z);
- else
- nres_premult(_MIPP_ p->Z,mr_mip->Bsize,p->Z);
-
- nres_modadd(_MIPP_ p->X,p->Y,mr_mip->w2); /* C=A+U */
- nres_modsub(_MIPP_ p->X,p->Y,mr_mip->w3); /* D=A-U */
-
- nres_modmult(_MIPP_ mr_mip->w2,mr_mip->w3,p->X); /* X=C.D */
-
- nres_modsub(_MIPP_ mr_mip->w2,p->Z,mr_mip->w2); /* C-2dZ^2 */
- nres_modmult(_MIPP_ mr_mip->w2,mr_mip->w1,p->Y); /* Y=E.(C-2dZ^2) */
- nres_modmult(_MIPP_ mr_mip->w3,mr_mip->w1,p->Z); /* Z=D.E */
-
- p->marker=MR_EPOINT_GENERAL;
- return;
-}
-
-static BOOL ecurve_padd(_MIPD_ epoint *p,epoint *pa)
-{ /* primitive add two epoints on the active ecurve - pa+=p; *
- * note that if p is normalized, its Z coordinate isn't used */
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- if (p->marker==MR_EPOINT_INFINITY) return TRUE;
- if (pa->marker==MR_EPOINT_INFINITY)
- {
- epoint_copy(p,pa);
- return TRUE;
- }
-
- nres_modadd(_MIPP_ p->X,p->Y,mr_mip->w1);
- nres_modadd(_MIPP_ pa->X,pa->Y,mr_mip->w2);
- nres_modmult(_MIPP_ mr_mip->w1,mr_mip->w2,mr_mip->w1); /* I=(X1+Y1)(X2+Y2) */
- if (p->marker!=MR_EPOINT_NORMALIZED)
- {
- if (pa->marker==MR_EPOINT_NORMALIZED)
- copy(p->Z,pa->Z);
- else nres_modmult(_MIPP_ p->Z,pa->Z,pa->Z); /* z = A = Z1*Z2 */
- }
- else
- {
- if (pa->marker==MR_EPOINT_NORMALIZED) copy(mr_mip->one,pa->Z);
- }
-
- nres_modmult(_MIPP_ pa->Z,pa->Z,mr_mip->w2); /* w2 = B = dA^2 */
- if (mr_abs(mr_mip->Bsize)==MR_TOOBIG)
- nres_modmult(_MIPP_ mr_mip->w2,mr_mip->B,mr_mip->w2);
- else
- nres_premult(_MIPP_ mr_mip->w2,mr_mip->Bsize,mr_mip->w2);
- nres_modmult(_MIPP_ p->X,pa->X,pa->X); /* x = C = X1*X2 */
- nres_modmult(_MIPP_ p->Y,pa->Y,pa->Y); /* y = D = Y1*Y2 */
- nres_modmult(_MIPP_ pa->X,pa->Y,mr_mip->w3); /* w3 = E = C*D */
-
- nres_modsub(_MIPP_ mr_mip->w1,pa->X,mr_mip->w1);
- nres_modsub(_MIPP_ mr_mip->w1,pa->Y,mr_mip->w1); /* I=(X1+Y1)(X2+Y2)-C-D =X1*Y2+Y1*X2 */
-
- if (mr_abs(mr_mip->Asize)==MR_TOOBIG) /* */
- nres_modmult(_MIPP_ pa->Y,mr_mip->A,pa->Y);
- else
- nres_premult(_MIPP_ pa->Y,mr_mip->Asize,pa->Y);
- nres_modsub(_MIPP_ pa->X,pa->Y,pa->X); /* X = H = C-aD */
-
- nres_modmult(_MIPP_ pa->Z,pa->X,pa->Z);
- nres_modmult(_MIPP_ pa->Z,mr_mip->w1,pa->Z);
-
- nres_modsub(_MIPP_ mr_mip->w3,mr_mip->w2,pa->Y);
- nres_modmult(_MIPP_ pa->Y,mr_mip->w1,pa->Y);
-
- nres_modadd(_MIPP_ mr_mip->w3,mr_mip->w2,mr_mip->w3);
- nres_modmult(_MIPP_ pa->X,mr_mip->w3,pa->X);
-
- if (size(pa->Z)==0)
- {
- copy(mr_mip->one,pa->X);
- zero(pa->Y);
- pa->marker=MR_EPOINT_INFINITY;
- }
- else pa->marker=MR_EPOINT_GENERAL;
-
- return TRUE;
-}
-
-void epoint_copy(epoint *a,epoint *b)
-{
- if (a==b || b==NULL) return;
-
- copy(a->X,b->X);
- copy(a->Y,b->Y);
- copy(a->Z,b->Z);
-
- b->marker=a->marker;
- return;
-}
-
-BOOL epoint_comp(_MIPD_ epoint *a,epoint *b)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return FALSE;
- if (a==b) return TRUE;
- if (a->marker==MR_EPOINT_INFINITY)
- {
- if (b->marker==MR_EPOINT_INFINITY) return TRUE;
- else return FALSE;
- }
- if (b->marker==MR_EPOINT_INFINITY)
- return FALSE;
-
- MR_IN(105)
- copy(a->Z,mr_mip->w1);
- copy(b->Z,mr_mip->w2);
-
- nres_modmult(_MIPP_ a->X,b->Z,mr_mip->w1);
- nres_modmult(_MIPP_ b->X,a->Z,mr_mip->w2);
-
- if (mr_compare(mr_mip->w1,mr_mip->w2)!=0)
- {
- MR_OUT
- return FALSE;
- }
-
- nres_modmult(_MIPP_ a->Y,b->Z,mr_mip->w1);
- nres_modmult(_MIPP_ b->Y,a->Z,mr_mip->w2);
-
- if (mr_compare(mr_mip->w1,mr_mip->w2)!=0)
- {
- MR_OUT
- return FALSE;
- }
- MR_OUT
- return TRUE;
-
-}
-
-int ecurve_add(_MIPD_ epoint *p,epoint *pa)
-{ /* pa=pa+p; */
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return MR_OVER;
-
- MR_IN(94)
-
- if (p==pa)
- {
- ecurve_double(_MIPP_ pa);
- MR_OUT
- if (pa->marker==MR_EPOINT_INFINITY) return MR_OVER;
- return MR_DOUBLE;
- }
- if (pa->marker==MR_EPOINT_INFINITY)
- {
- epoint_copy(p,pa);
- MR_OUT
- return MR_ADD;
- }
- if (p->marker==MR_EPOINT_INFINITY)
- {
- MR_OUT
- return MR_ADD;
- }
-
- if (!ecurve_padd(_MIPP_ p,pa))
- {
- ecurve_double(_MIPP_ pa);
- MR_OUT
- return MR_DOUBLE;
- }
- MR_OUT
- if (pa->marker==MR_EPOINT_INFINITY) return MR_OVER;
- return MR_ADD;
-}
-
-void epoint_negate(_MIPD_ epoint *p)
-{ /* negate a point */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
- if (p->marker==MR_EPOINT_INFINITY) return;
-
- MR_IN(121)
- if (size(p->X)!=0) mr_psub(_MIPP_ mr_mip->modulus,p->X,p->X);
- MR_OUT
-}
-
-int ecurve_sub(_MIPD_ epoint *p,epoint *pa)
-{
- int r;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return MR_OVER;
-
- MR_IN(104)
-
- if (p==pa)
- {
- epoint_set(_MIPP_ NULL,NULL,0,pa);
- MR_OUT
- return MR_OVER;
- }
- if (p->marker==MR_EPOINT_INFINITY)
- {
- MR_OUT
- return MR_ADD;
- }
-
- epoint_negate(_MIPP_ p);
- r=ecurve_add(_MIPP_ p,pa);
- epoint_negate(_MIPP_ p);
-
- MR_OUT
- return r;
-}
-
-int ecurve_mult(_MIPD_ big e,epoint *pa,epoint *pt)
-{ /* pt=e*pa; */
- int i,j,n,nb,nbs,nzs,nadds;
- epoint *table[MR_ECC_STORE_N];
-
-#ifdef MR_STATIC
- char mem[MR_ECP_RESERVE(MR_ECC_STORE_N)];
-#else
- char *mem;
-#endif
-
-#ifndef MR_ALWAYS_BINARY
- epoint *p;
- int ce,ch;
-#endif
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return 0;
-
- MR_IN(95)
- if (size(e)==0)
- { /* multiplied by 0 */
- epoint_set(_MIPP_ NULL,NULL,0,pt);
- MR_OUT
- return 0;
- }
- copy(e,mr_mip->w9);
- epoint_copy(pa,pt);
-
- if (size(mr_mip->w9)<0)
- { /* pt = -pt */
- negify(mr_mip->w9,mr_mip->w9);
- epoint_negate(_MIPP_ pt);
- }
-
- if (size(mr_mip->w9)==1)
- {
- MR_OUT
- return 0;
- }
-
- premult(_MIPP_ mr_mip->w9,3,mr_mip->w10); /* h=3*e */
-
-#ifndef MR_STATIC
-#ifndef MR_ALWAYS_BINARY
- if (mr_mip->base==mr_mip->base2)
- {
-#endif
-#endif
-
-#ifdef MR_STATIC
- memset(mem,0,MR_ECP_RESERVE(MR_ECC_STORE_N));
-#else
- mem=(char *)ecp_memalloc(_MIPP_ MR_ECC_STORE_N);
-#endif
-
- for (i=0;i<=MR_ECC_STORE_N-1;i++)
- table[i]=epoint_init_mem(_MIPP_ mem,i);
-
- epoint_copy(pt,table[0]);
- epoint_copy(table[0],table[MR_ECC_STORE_N-1]);
- ecurve_double(_MIPP_ table[MR_ECC_STORE_N-1]);
-
- for (i=1;iw10);
- nadds=0;
- epoint_set(_MIPP_ NULL,NULL,0,pt);
- for (i=nb-1;i>=1;)
- { /* add/subtract */
- if (mr_mip->user!=NULL) (*mr_mip->user)();
- n=mr_naf_window(_MIPP_ mr_mip->w9,mr_mip->w10,i,&nbs,&nzs,MR_ECC_STORE_N);
- for (j=0;j0) {ecurve_add(_MIPP_ table[n/2],pt); nadds++;}
- if (n<0) {ecurve_sub(_MIPP_ table[(-n)/2],pt); nadds++;}
- i-=nbs;
- if (nzs)
- {
- for (j=0;jw10)-1,mr_mip->w11);
- mr_psub(_MIPP_ mr_mip->w10,mr_mip->w11,mr_mip->w10);
- subdiv(_MIPP_ mr_mip->w11,2,mr_mip->w11);
- while (size(mr_mip->w11) > 1)
- { /* add/subtract method */
- if (mr_mip->user!=NULL) (*mr_mip->user)();
-
- ecurve_double(_MIPP_ pt);
- ce=mr_compare(mr_mip->w9,mr_mip->w11); /* e(i)=1? */
- ch=mr_compare(mr_mip->w10,mr_mip->w11); /* h(i)=1? */
- if (ch>=0)
- { /* h(i)=1 */
- if (ce<0) {ecurve_add(_MIPP_ p,pt); nadds++;}
- mr_psub(_MIPP_ mr_mip->w10,mr_mip->w11,mr_mip->w10);
- }
- if (ce>=0)
- { /* e(i)=1 */
- if (ch<0) {ecurve_sub(_MIPP_ p,pt); nadds++;}
- mr_psub(_MIPP_ mr_mip->w9,mr_mip->w11,mr_mip->w9);
- }
- subdiv(_MIPP_ mr_mip->w11,2,mr_mip->w11);
- }
- ecp_memkill(_MIPP_ mem,1);
- }
-#endif
-#endif
- MR_OUT
- return nadds;
-}
-
-#ifndef MR_NO_ECC_MULTIADD
-#ifndef MR_STATIC
-
-void ecurve_multn(_MIPD_ int n,big *y,epoint **x,epoint *w)
-{ /* pt=e[0]*p[0]+e[1]*p[1]+ .... e[n-1]*p[n-1] */
- int i,j,k,m,nb,ea;
- epoint **G;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(114)
-
- m=1< nb) nb=k;
-
- epoint_set(_MIPP_ NULL,NULL,0,w); /* w=0 */
-
-#ifndef MR_ALWAYS_BINARY
- if (mr_mip->base==mr_mip->base2)
- {
-#endif
- for (i=nb-1;i>=0;i--)
- {
- if (mr_mip->user!=NULL) (*mr_mip->user)();
- ea=0;
- k=1;
- for (j=0;jmarker==MR_EPOINT_NORMALIZED)
- {
- if (Q->marker==MR_EPOINT_NORMALIZED)
- copy(mr_mip->one,mr_mip->w1);
- else copy(Q->Z,mr_mip->w1);
- }
- else
- {
- if (Q->marker==MR_EPOINT_NORMALIZED)
- copy(P->Z,mr_mip->w1);
- else nres_modmult(_MIPP_ P->Z,Q->Z,mr_mip->w1); /* w1 = A = Z1*Z2 */
- }
- nres_modmult(_MIPP_ mr_mip->w1,mr_mip->w1,mr_mip->w2); /* w2 = B = dA^2 */
- if (mr_abs(mr_mip->Bsize)==MR_TOOBIG)
- nres_modmult(_MIPP_ mr_mip->w2,mr_mip->B,mr_mip->w2);
- else
- nres_premult(_MIPP_ mr_mip->w2,mr_mip->Bsize,mr_mip->w2);
- nres_modmult(_MIPP_ P->X,Q->X,mr_mip->w3); /* w3 = C = X1*X2 */
- nres_modmult(_MIPP_ P->Y,Q->Y,mr_mip->w4); /* w4 = D = Y1*Y2 */
- nres_modmult(_MIPP_ mr_mip->w3,mr_mip->w4,mr_mip->w5); /* w5 = E = C*D */
- nres_modmult(_MIPP_ P->X,Q->Y,mr_mip->w7); /* w7 = F = X1.Y2 */
- nres_modmult(_MIPP_ Q->X,P->Y,mr_mip->w8); /* w8 = G = X2.Y1 */
-
- if (mr_abs(mr_mip->Asize)==MR_TOOBIG) /* w4 = aD */
- nres_modmult(_MIPP_ mr_mip->w4,mr_mip->A,mr_mip->w4);
- else
- nres_premult(_MIPP_ mr_mip->w4,mr_mip->Asize,mr_mip->w4);
-
-/* P+Q */
-
- nres_modsub(_MIPP_ mr_mip->w3,mr_mip->w4,mr_mip->w6); /* w6 = H = C-aD */
- nres_modadd(_MIPP_ mr_mip->w7,mr_mip->w8,PP->Z); /* X1*Y2+X2*Y1 */
- nres_modadd(_MIPP_ mr_mip->w5,mr_mip->w2,PP->X);
- nres_modmult(_MIPP_ PP->X,mr_mip->w6,PP->X);
- nres_modsub(_MIPP_ mr_mip->w5,mr_mip->w2,PP->Y);
- nres_modmult(_MIPP_ PP->Y,PP->Z,PP->Y);
- nres_modmult(_MIPP_ PP->Z,mr_mip->w6,PP->Z);
- nres_modmult(_MIPP_ PP->Z,mr_mip->w1,PP->Z);
-
- if (size(PP->Z)==0)
- {
- copy(mr_mip->one,PP->X);
- zero(PP->Y);
- PP->marker=MR_EPOINT_INFINITY;
- }
- else PP->marker=MR_EPOINT_GENERAL;
-
-/* P-Q */
-
- nres_modadd(_MIPP_ mr_mip->w3,mr_mip->w4,mr_mip->w6); /* w6 = C+aD */
- nres_modsub(_MIPP_ mr_mip->w8,mr_mip->w7,PM->Z); /* X2*Y1-X1*Y2 */
- nres_modsub(_MIPP_ mr_mip->w5,mr_mip->w2,PM->X);
- nres_modmult(_MIPP_ PM->X,mr_mip->w6,PM->X);
- nres_modadd(_MIPP_ mr_mip->w5,mr_mip->w2,PM->Y);
- nres_modmult(_MIPP_ PM->Y,PM->Z,PM->Y);
- nres_modmult(_MIPP_ PM->Z,mr_mip->w6,PM->Z);
- nres_modmult(_MIPP_ PM->Z,mr_mip->w1,PM->Z);
-
- if (size(PM->Z)==0)
- {
- copy(mr_mip->one,PM->X);
- zero(PM->Y);
- PM->marker=MR_EPOINT_INFINITY;
- }
- else PM->marker=MR_EPOINT_GENERAL;
-
- return TRUE;
-}
-
-void ecurve_mult2(_MIPD_ big e,epoint *p,big ea,epoint *pa,epoint *pt)
-{ /* pt=e*p+ea*pa; */
- int e1,h1,e2,h2,bb;
- epoint *p1,*p2,*ps[2];
-#ifdef MR_STATIC
- char mem[MR_ECP_RESERVE(4)];
-#else
- char *mem;
-#endif
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- if (mr_mip->ERNUM) return;
-
- MR_IN(103)
-
- if (size(e)==0)
- {
- ecurve_mult(_MIPP_ ea,pa,pt);
- MR_OUT
- return;
- }
-#ifdef MR_STATIC
- memset(mem,0,MR_ECP_RESERVE(4));
-#else
- mem=ecp_memalloc(_MIPP_ 4);
-#endif
- p2=epoint_init_mem(_MIPP_ mem,0);
- p1=epoint_init_mem(_MIPP_ mem,1);
- ps[0]=epoint_init_mem(_MIPP_ mem,2);
- ps[1]=epoint_init_mem(_MIPP_ mem,3);
-
- epoint_copy(pa,p2);
- copy(ea,mr_mip->w9);
- if (size(mr_mip->w9)<0)
- { /* p2 = -p2 */
- negify(mr_mip->w9,mr_mip->w9);
- epoint_negate(_MIPP_ p2);
- }
-
- epoint_copy(p,p1);
- copy(e,mr_mip->w12);
- if (size(mr_mip->w12)<0)
- { /* p1= -p1 */
- negify(mr_mip->w12,mr_mip->w12);
- epoint_negate(_MIPP_ p1);
- }
-
- epoint_set(_MIPP_ NULL,NULL,0,pt); /* pt=0 */
- ecurve_add_sub(_MIPP_ p1,p2,ps[0],ps[1]); /* ps[0]=p1+p2, ps[1]=p1-p2 */
-
- mr_jsf(_MIPP_ mr_mip->w9,mr_mip->w12,mr_mip->w10,mr_mip->w9,mr_mip->w13,mr_mip->w12);
-
-/* To use a simple NAF instead, substitute this for the JSF
- premult(_MIPP_ mr_mip->w9,3,mr_mip->w10); 3*ea
- premult(_MIPP_ mr_mip->w12,3,mr_mip->w13); 3*e
-*/
-
-#ifndef MR_ALWAYS_BINARY
- if (mr_mip->base==mr_mip->base2)
- {
-#endif
- if (mr_compare(mr_mip->w10,mr_mip->w13)>=0) bb=logb2(_MIPP_ mr_mip->w10)-1;
- else bb=logb2(_MIPP_ mr_mip->w13)-1;
-
- while (bb>=0) /* for the simple NAF, this should be 1 */
- {
- if (mr_mip->user!=NULL) (*mr_mip->user)();
- ecurve_double(_MIPP_ pt);
-
- e1=h1=e2=h2=0;
- if (mr_testbit(_MIPP_ mr_mip->w9,bb)) e2=1;
- if (mr_testbit(_MIPP_ mr_mip->w10,bb)) h2=1;
- if (mr_testbit(_MIPP_ mr_mip->w12,bb)) e1=1;
- if (mr_testbit(_MIPP_ mr_mip->w13,bb)) h1=1;
-
- if (e1!=h1)
- {
- if (e2==h2)
- {
- if (h1==1) ecurve_add(_MIPP_ p1,pt);
- else ecurve_sub(_MIPP_ p1,pt);
- }
- else
- {
- if (h1==1)
- {
- if (h2==1) ecurve_add(_MIPP_ ps[0],pt);
- else ecurve_add(_MIPP_ ps[1],pt);
- }
- else
- {
- if (h2==1) ecurve_sub(_MIPP_ ps[1],pt);
- else ecurve_sub(_MIPP_ ps[0],pt);
- }
- }
- }
- else if (e2!=h2)
- {
- if (h2==1) ecurve_add(_MIPP_ p2,pt);
- else ecurve_sub(_MIPP_ p2,pt);
- }
- bb-=1;
- }
-#ifndef MR_ALWAYS_BINARY
- }
- else
- {
- if (mr_compare(mr_mip->w10,mr_mip->w13)>=0)
- expb2(_MIPP_ logb2(_MIPP_ mr_mip->w10)-1,mr_mip->w11);
- else expb2(_MIPP_ logb2(_MIPP_ mr_mip->w13)-1,mr_mip->w11);
-
- while (size(mr_mip->w11) > 0) /* for the NAF, this should be 1 */
- { /* add/subtract method */
- if (mr_mip->user!=NULL) (*mr_mip->user)();
-
- ecurve_double(_MIPP_ pt);
-
- e1=h1=e2=h2=0;
- if (mr_compare(mr_mip->w9,mr_mip->w11)>=0)
- { /* e1(i)=1? */
- e2=1;
- mr_psub(_MIPP_ mr_mip->w9,mr_mip->w11,mr_mip->w9);
- }
- if (mr_compare(mr_mip->w10,mr_mip->w11)>=0)
- { /* h1(i)=1? */
- h2=1;
- mr_psub(_MIPP_ mr_mip->w10,mr_mip->w11,mr_mip->w10);
- }
- if (mr_compare(mr_mip->w12,mr_mip->w11)>=0)
- { /* e2(i)=1? */
- e1=1;
- mr_psub(_MIPP_ mr_mip->w12,mr_mip->w11,mr_mip->w12);
- }
- if (mr_compare(mr_mip->w13,mr_mip->w11)>=0)
- { /* h2(i)=1? */
- h1=1;
- mr_psub(_MIPP_ mr_mip->w13,mr_mip->w11,mr_mip->w13);
- }
-
- if (e1!=h1)
- {
- if (e2==h2)
- {
- if (h1==1) ecurve_add(_MIPP_ p1,pt);
- else ecurve_sub(_MIPP_ p1,pt);
- }
- else
- {
- if (h1==1)
- {
- if (h2==1) ecurve_add(_MIPP_ ps[0],pt);
- else ecurve_add(_MIPP_ ps[1],pt);
- }
- else
- {
- if (h2==1) ecurve_sub(_MIPP_ ps[1],pt);
- else ecurve_sub(_MIPP_ ps[0],pt);
- }
- }
- }
- else if (e2!=h2)
- {
- if (h2==1) ecurve_add(_MIPP_ p2,pt);
- else ecurve_sub(_MIPP_ p2,pt);
- }
-
- subdiv(_MIPP_ mr_mip->w11,2,mr_mip->w11);
- }
- }
-#endif
- ecp_memkill(_MIPP_ mem,4);
- MR_OUT
-}
-
-#endif
-
-#endif
diff --git a/crypto/sm2/miracl/mrjack.c b/crypto/sm2/miracl/mrjack.c
deleted file mode 100644
index 1b77a984..00000000
--- a/crypto/sm2/miracl/mrjack.c
+++ /dev/null
@@ -1,342 +0,0 @@
-
-/***************************************************************************
- *
-Copyright 2013 CertiVox IOM Ltd. *
- *
-This file is part of CertiVox MIRACL Crypto SDK. *
- *
-The CertiVox MIRACL Crypto SDK provides developers with an *
-extensive and efficient set of cryptographic functions. *
-For further information about its features and functionalities please *
-refer to http://www.certivox.com *
- *
-* The CertiVox MIRACL Crypto SDK is free software: you can *
- redistribute it and/or modify it under the terms of the *
- GNU Affero General Public License as published by the *
- Free Software Foundation, either version 3 of the License, *
- or (at your option) any later version. *
- *
-* The CertiVox MIRACL Crypto SDK is distributed in the hope *
- that it will be useful, but WITHOUT ANY WARRANTY; without even the *
- implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. *
- See the GNU Affero General Public License for more details. *
- *
-* You should have received a copy of the GNU Affero General Public *
- License along with CertiVox MIRACL Crypto SDK. *
- If not, see . *
- *
-You can be released from the requirements of the license by purchasing *
-a commercial license. Buying such a license is mandatory as soon as you *
-develop commercial activities involving the CertiVox MIRACL Crypto SDK *
-without disclosing the source code of your own applications, or shipping *
-the CertiVox MIRACL Crypto SDK with a closed source product. *
- *
-***************************************************************************/
-/*
- * MIRACL Jacobi symbol routine
- * mrjack.c
- *
- * See "A binary algorithm for the Jacobi symbol"
- * Shallit and Sorenson
- */
-#include
-#include
-
-int jack(_MIPD_ big a,big n)
-{ /* find jacobi symbol (a/n), for positive odd n */
- big w;
- int nm8,onm8,t;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM || size(a)==0 || size(n) <1) return 0;
- MR_IN(3)
-
- t=1;
- copy(n,mr_mip->w2);
- nm8=remain(_MIPP_ mr_mip->w2,8);
- if (nm8%2==0)
- {
- MR_OUT
- return 0;
- }
-
- if (size(a)<0)
- {
- if (nm8%4==3) t=-1;
- negify(a,mr_mip->w1);
- }
- else copy(a,mr_mip->w1);
-
- while (size(mr_mip->w1)!=0)
- {
- while (remain(_MIPP_ mr_mip->w1,2)==0)
- {
- subdiv(_MIPP_ mr_mip->w1,2,mr_mip->w1);
- if (nm8==3 || nm8==5) t=-t;
- }
- if (mr_compare(mr_mip->w1,mr_mip->w2)<0)
- {
- onm8=nm8;
- w=mr_mip->w1; mr_mip->w1=mr_mip->w2; mr_mip->w2=w;
- nm8=remain(_MIPP_ mr_mip->w2,8);
- if (onm8%4==3 && nm8%4==3) t=-t;
- }
- mr_psub(_MIPP_ mr_mip->w1,mr_mip->w2,mr_mip->w1);
- subdiv(_MIPP_ mr_mip->w1,2,mr_mip->w1);
-
- if (nm8==3 || nm8==5) t=-t;
- }
-
- MR_OUT
- if (size(mr_mip->w2)==1) return t;
- return 0;
-}
-
-/*
- * See "Efficient Algorithms for Computing the Jacobi Symbol"
- * Eikenberry & Sorenson
- *
- * Its turns out this is slower than the binary method above for reasonable sizes
- * of parameters (and takes up a lot more space!)
-
-
-#ifdef MR_FP
-#include
-#endif
-
-
-static void rfind(mr_small u,mr_small v,mr_small k,mr_small sk,mr_utype *a,mr_utype *b)
-{
- mr_utype x2,y2,r;
- mr_small w,q,x1,y1,sr;
-#ifdef MR_FP
- mr_small dres;
-#endif
-
- w=invers(v,k);
- w=smul(u,w,k);
-
- x1=k; x2=0;
- y1=w; y2=1;
-
-// NOTE: x1 and y1 are always +ve. x2 and y2 are always small
-
- while (y1>=sk)
- {
-#ifndef MR_NOFULLWIDTH
- if (x1==0) q=muldvm((mr_small)1,(mr_small)0,y1,&sr);
- else
-#endif
- q=MR_DIV(x1,y1);
- r= x1-q*y1; x1=y1; y1=r;
- sr=x2-q*y2; x2=y2; y2=sr;
- }
- if (y2>=0) { *a=y2; *b=0-y1; }
- else { *a=-y2; *b=y1; }
-}
-
-int jack(_MIPD_ big U,big V)
-{ // find jacobi symbol for U wrt V. Only defined for
- // positive V, V odd. Otherwise returns 0
- int i,e,r,m,t,v8,u4;
- mr_utype a,b;
- mr_small u,v,d,g,k,sk,s;
-#ifdef MR_FP
- mr_small dres;
-#endif
- big w;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-#ifdef MR_FP_ROUNDING
- mr_large ik,id;
-#endif
- if (mr_mip->ERNUM || size(U)==0 || size(V) <1) return 0;
- copy(U,mr_mip->w1);
- copy(V,mr_mip->w2);
- a=0;
- MR_IN(3)
-
- if (remain(_MIPP_ mr_mip->w2,2)==0)
- { // V is even
- MR_OUT
- return 0;
- }
-
- if (mr_mip->base!=0)
- {
- k=1;
- for (m=1;;m++)
- {
- k*=2;
- if (k==MAXBASE) break;
- }
- if (m%2==1) {m--; k=MR_DIV(k,2);}
-#ifdef MR_FP_ROUNDING
- ik=mr_invert(k);
-#endif
- }
- else
- {
- m=MIRACL;
- k=0;
- }
- r=m/2;
- sk=1;
- for (i=0;iw2,8);
-
- while (!mr_mip->ERNUM && size(mr_mip->w1)!=0)
- {
- if (size(mr_mip->w1)<0)
- {
- negify(mr_mip->w1,mr_mip->w1);
- if (v8%4==3) t=-t;
- }
-
- do { // oddify
-
-#ifndef MR_ALWAYS_BINARY
- if (mr_mip->base==mr_mip->base2)
- {
-#endif
- if (mr_mip->base==k) u=mr_mip->w1->w[0];
- else u=MR_REMAIN(mr_mip->w1->w[0],k);
-#ifndef MR_ALWAYS_BINARY
- }
-
-#ifdef MR_FP_ROUNDING
- else u=mr_sdiv(_MIPP_ mr_mip->w1,k,ik,mr_mip->w3);
-#else
- else u=mr_sdiv(_MIPP_ mr_mip->w1,k,mr_mip->w3);
-#endif
-
-#endif
- if (u==0) {s=k; e=0;}
- else
- {
- s=1; e=0;
- while (MR_REMAIN(u,2)==0) {s*=2; e++; u=MR_DIV(u,2);}
- }
- if (s==mr_mip->base) mr_shift(_MIPP_ mr_mip->w1,-1,mr_mip->w1);
-#ifdef MR_FP_ROUNDING
- else if (s>1)
- {
- mr_sdiv(_MIPP_ mr_mip->w1,s,mr_invert(s),mr_mip->w1);
- }
-#else
- else if (s>1) mr_sdiv(_MIPP_ mr_mip->w1,s,mr_mip->w1);
-#endif
- } while (u==0);
- if (e%2!=0 && (v8==3 || v8==5)) t=-t;
- if (mr_compare(mr_mip->w1,mr_mip->w2)<0)
- {
- if (mr_mip->base==mr_mip->base2) u4=(int)MR_REMAIN(mr_mip->w1->w[0],4);
- else u4=remain(_MIPP_ mr_mip->w1,4);
- if (v8%4==3 && u4==3) t=-t;
- w=mr_mip->w1; mr_mip->w1=mr_mip->w2; mr_mip->w2=w;
- }
-
-#ifndef MR_ALWAYS_BINARY
- if (mr_mip->base==mr_mip->base2)
- {
-#endif
- if (k==mr_mip->base)
- {
- u=mr_mip->w1->w[0];
- v=mr_mip->w2->w[0];
- }
- else
- {
- u=MR_REMAIN(mr_mip->w1->w[0],k);
- v=MR_REMAIN(mr_mip->w2->w[0],k);
- }
-#ifndef MR_ALWAYS_BINARY
- }
- else
- {
-#ifdef MR_FP_ROUNDING
- u=mr_sdiv(_MIPP_ mr_mip->w1,k,ik,mr_mip->w3);
- v=mr_sdiv(_MIPP_ mr_mip->w2,k,ik,mr_mip->w3);
-#else
- u=mr_sdiv(_MIPP_ mr_mip->w1,k,mr_mip->w3);
- v=mr_sdiv(_MIPP_ mr_mip->w2,k,mr_mip->w3);
-#endif
- }
-#endif
- rfind(u,v,k,sk,&a,&b);
- if (a>1)
- {
-#ifdef MR_FP_ROUNDING
- d=mr_sdiv(_MIPP_ mr_mip->w2,a,mr_invert(a),mr_mip->w3);
-#else
- d=mr_sdiv(_MIPP_ mr_mip->w2,a,mr_mip->w3);
-#endif
- d=sgcd(d,a);
- a=MR_DIV(a,d);
- }
- else d=1;
-
- if (d>1)
- {
-#ifdef MR_FP_ROUNDING
- id=mr_invert(d);
- mr_sdiv(_MIPP_ mr_mip->w2,d,id,mr_mip->w2);
- u=mr_sdiv(_MIPP_ mr_mip->w1,d,id,mr_mip->w3);
-#else
- mr_sdiv(_MIPP_ mr_mip->w2,d,mr_mip->w2);
- u=mr_sdiv(_MIPP_ mr_mip->w1,d,mr_mip->w3);
-#endif
- }
- else u=0;
-
- g=a;
- if (mr_mip->base==mr_mip->base2) v8=(int)MR_REMAIN(mr_mip->w2->w[0],8);
- else v8=remain(_MIPP_ mr_mip->w2,8);
- while (MR_REMAIN(g,2)==0)
- {
- g=MR_DIV(g,2);
- if (v8==3 || v8==5) t=-t;
- }
- if (MR_REMAIN(g,4)==3 && v8%4==3) t=-t;
-#ifdef MR_FP_ROUNDING
- v=mr_sdiv(_MIPP_ mr_mip->w2,g,mr_invert(g),mr_mip->w3);
-#else
- v=mr_sdiv(_MIPP_ mr_mip->w2,g,mr_mip->w3);
-#endif
- t*=jac(v,g)*jac(u,d);
- if (t==0)
- {
- MR_OUT
- return 0;
- }
-
-// printf("a= %I64d b=%I64d %d\n",a,b,(int)b);
-
- if (a>1) mr_pmul(_MIPP_ mr_mip->w1,a,mr_mip->w1);
- if (b>=0)
- mr_pmul(_MIPP_ mr_mip->w2,b,mr_mip->w3);
- else
- {
- b=-b;
- mr_pmul(_MIPP_ mr_mip->w2,b,mr_mip->w3);
- negify(mr_mip->w3,mr_mip->w3);
- }
- // premult(_MIPP_ mr_mip->w2,(int)b,mr_mip->w3); <- nasty bug - potential loss of precision in b
- add(_MIPP_ mr_mip->w1,mr_mip->w3,mr_mip->w1);
- if (k==mr_mip->base) mr_shift(_MIPP_ mr_mip->w1,-1,mr_mip->w1);
-#ifdef MR_FP_ROUNDING
- else mr_sdiv(_MIPP_ mr_mip->w1,k,ik,mr_mip->w1);
-#else
- else mr_sdiv(_MIPP_ mr_mip->w1,k,mr_mip->w1);
-#endif
- }
- MR_OUT
- if (size(mr_mip->w2)==1) return t;
- return 0;
-}
-
-*/
diff --git a/crypto/sm2/miracl/mrlucas.c b/crypto/sm2/miracl/mrlucas.c
deleted file mode 100644
index 2a19b49f..00000000
--- a/crypto/sm2/miracl/mrlucas.c
+++ /dev/null
@@ -1,157 +0,0 @@
-
-/***************************************************************************
- *
-Copyright 2013 CertiVox IOM Ltd. *
- *
-This file is part of CertiVox MIRACL Crypto SDK. *
- *
-The CertiVox MIRACL Crypto SDK provides developers with an *
-extensive and efficient set of cryptographic functions. *
-For further information about its features and functionalities please *
-refer to http://www.certivox.com *
- *
-* The CertiVox MIRACL Crypto SDK is free software: you can *
- redistribute it and/or modify it under the terms of the *
- GNU Affero General Public License as published by the *
- Free Software Foundation, either version 3 of the License, *
- or (at your option) any later version. *
- *
-* The CertiVox MIRACL Crypto SDK is distributed in the hope *
- that it will be useful, but WITHOUT ANY WARRANTY; without even the *
- implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. *
- See the GNU Affero General Public License for more details. *
- *
-* You should have received a copy of the GNU Affero General Public *
- License along with CertiVox MIRACL Crypto SDK. *
- If not, see . *
- *
-You can be released from the requirements of the license by purchasing *
-a commercial license. Buying such a license is mandatory as soon as you *
-develop commercial activities involving the CertiVox MIRACL Crypto SDK *
-without disclosing the source code of your own applications, or shipping *
-the CertiVox MIRACL Crypto SDK with a closed source product. *
- *
-***************************************************************************/
-/*
- * MIRACL methods for evaluating lucas V function
- * mrlucas.c (Postl's algorithm)
- */
-
-#include
-#include
-
-void nres_lucas(_MIPD_ big p,big r,big vp,big v)
-{
- int i,nb;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(107)
-
- if (size(r)==0)
- {
- zero(vp);
- convert(_MIPP_ 2,v);
- nres(_MIPP_ v,v);
- MR_OUT
- return;
- }
- if (size(r)==1 || size(r)==(-1))
- { /* note - sign of r doesn't matter */
- convert(_MIPP_ 2,vp);
- nres(_MIPP_ vp,vp);
- copy(p,v);
- MR_OUT
- return;
- }
-
- copy(p,mr_mip->w3);
-
- convert(_MIPP_ 2,mr_mip->w4);
- nres(_MIPP_ mr_mip->w4,mr_mip->w4); /* w4=2 */
-
- copy(mr_mip->w4,mr_mip->w8);
- copy(mr_mip->w3,mr_mip->w9);
-
- copy(r,mr_mip->w1);
- insign(PLUS,mr_mip->w1);
- decr(_MIPP_ mr_mip->w1,1,mr_mip->w1);
-
-#ifndef MR_ALWAYS_BINARY
- if (mr_mip->base==mr_mip->base2)
- {
-#endif
- nb=logb2(_MIPP_ mr_mip->w1);
- for (i=nb-1;i>=0;i--)
- {
- if (mr_mip->user!=NULL) (*mr_mip->user)();
-
- if (mr_testbit(_MIPP_ mr_mip->w1,i))
- {
- nres_modmult(_MIPP_ mr_mip->w8,mr_mip->w9,mr_mip->w8);
- nres_modsub(_MIPP_ mr_mip->w8,mr_mip->w3,mr_mip->w8);
- nres_modmult(_MIPP_ mr_mip->w9,mr_mip->w9,mr_mip->w9);
- nres_modsub(_MIPP_ mr_mip->w9,mr_mip->w4,mr_mip->w9);
-
- }
- else
- {
- nres_modmult(_MIPP_ mr_mip->w9,mr_mip->w8,mr_mip->w9);
- nres_modsub(_MIPP_ mr_mip->w9,mr_mip->w3,mr_mip->w9);
- nres_modmult(_MIPP_ mr_mip->w8,mr_mip->w8,mr_mip->w8);
- nres_modsub(_MIPP_ mr_mip->w8,mr_mip->w4,mr_mip->w8);
- }
- }
-
-#ifndef MR_ALWAYS_BINARY
- }
- else
- {
- expb2(_MIPP_ logb2(_MIPP_ mr_mip->w1)-1,mr_mip->w2);
-
- while (!mr_mip->ERNUM && size(mr_mip->w2)!=0)
- { /* use binary method */
- if (mr_compare(mr_mip->w1,mr_mip->w2)>=0)
- { /* vp=v*vp-p, v=v*v-2 */
- nres_modmult(_MIPP_ mr_mip->w8,mr_mip->w9,mr_mip->w8);
- nres_modsub(_MIPP_ mr_mip->w8,mr_mip->w3,mr_mip->w8);
- nres_modmult(_MIPP_ mr_mip->w9,mr_mip->w9,mr_mip->w9);
- nres_modsub(_MIPP_ mr_mip->w9,mr_mip->w4,mr_mip->w9);
- subtract(_MIPP_ mr_mip->w1,mr_mip->w2,mr_mip->w1);
- }
- else
- { /* v=v*vp-p, vp=vp*vp-2 */
- nres_modmult(_MIPP_ mr_mip->w9,mr_mip->w8,mr_mip->w9);
- nres_modsub(_MIPP_ mr_mip->w9,mr_mip->w3,mr_mip->w9);
- nres_modmult(_MIPP_ mr_mip->w8,mr_mip->w8,mr_mip->w8);
- nres_modsub(_MIPP_ mr_mip->w8,mr_mip->w4,mr_mip->w8);
- }
- subdiv(_MIPP_ mr_mip->w2,2,mr_mip->w2);
- }
- }
-#endif
-
- copy(mr_mip->w9,v);
- if (v!=vp) copy(mr_mip->w8,vp);
- MR_OUT
-
-}
-
-void lucas(_MIPD_ big p,big r,big n,big vp,big v)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(108)
- prepare_monty(_MIPP_ n);
- nres(_MIPP_ p,mr_mip->w3);
- nres_lucas(_MIPP_ mr_mip->w3,r,mr_mip->w8,mr_mip->w9);
- redc(_MIPP_ mr_mip->w9,v);
- if (v!=vp) redc(_MIPP_ mr_mip->w8,vp);
- MR_OUT
-}
-
diff --git a/crypto/sm2/miracl/mrmonty.c b/crypto/sm2/miracl/mrmonty.c
deleted file mode 100644
index 102b4d34..00000000
--- a/crypto/sm2/miracl/mrmonty.c
+++ /dev/null
@@ -1,1414 +0,0 @@
-
-/***************************************************************************
- *
-Copyright 2013 CertiVox IOM Ltd. *
- *
-This file is part of CertiVox MIRACL Crypto SDK. *
- *
-The CertiVox MIRACL Crypto SDK provides developers with an *
-extensive and efficient set of cryptographic functions. *
-For further information about its features and functionalities please *
-refer to http://www.certivox.com *
- *
-* The CertiVox MIRACL Crypto SDK is free software: you can *
- redistribute it and/or modify it under the terms of the *
- GNU Affero General Public License as published by the *
- Free Software Foundation, either version 3 of the License, *
- or (at your option) any later version. *
- *
-* The CertiVox MIRACL Crypto SDK is distributed in the hope *
- that it will be useful, but WITHOUT ANY WARRANTY; without even the *
- implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. *
- See the GNU Affero General Public License for more details. *
- *
-* You should have received a copy of the GNU Affero General Public *
- License along with CertiVox MIRACL Crypto SDK. *
- If not, see . *
- *
-You can be released from the requirements of the license by purchasing *
-a commercial license. Buying such a license is mandatory as soon as you *
-develop commercial activities involving the CertiVox MIRACL Crypto SDK *
-without disclosing the source code of your own applications, or shipping *
-the CertiVox MIRACL Crypto SDK with a closed source product. *
- *
-***************************************************************************/
-/*
- * MIRACL Montgomery's method for modular arithmetic without division.
- * mrmonty.c
- *
- * Programs to implement Montgomery's method
- * See "Modular Multiplication Without Trial Division", Math. Comp.
- * Vol 44, Number 170, April 1985, Pages 519-521
- * NOTE - there is an important correction to this paper mentioned as a
- * footnote in "Speeding the Pollard and Elliptic Curve Methods",
- * Math. Comput., Vol. 48, January 1987, 243-264
- *
- * The advantage of this approach is that no division required in order
- * to compute a modular reduction - useful if division is slow
- * e.g. on a SPARC processor, or a DSP.
- *
- * The disadvantage is that numbers must first be converted to an internal
- * "n-residue" form.
- *
- */
-
-#include
-#include
-
-#ifdef MR_FP
-#include
-#endif
-
-#ifdef MR_WIN64
-#include
-#endif
-
-#ifdef MR_COUNT_OPS
-extern int fpc,fpa;
-#endif
-
-#ifdef MR_CELL
-extern void mod256(_MIPD_ big,big);
-#endif
-
-void kill_monty(_MIPDO_ )
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- zero(mr_mip->modulus);
-#ifdef MR_KCM
- zero(mr_mip->big_ndash);
-#endif
-}
-
-mr_small prepare_monty(_MIPD_ big n)
-{ /* prepare Montgomery modulus */
-#ifdef MR_KCM
- int nl;
-#endif
-#ifdef MR_PENTIUM
- mr_small ndash;
- mr_small base;
- mr_small magic=13835058055282163712.0;
- int control=0x1FFF;
-#endif
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return (mr_small)0;
-/* Is it set-up already? */
- if (size(mr_mip->modulus)!=0)
- if (mr_compare(n,mr_mip->modulus)==0) return mr_mip->ndash;
-
- MR_IN(80)
-
- if (size(n)<=2)
- {
- mr_berror(_MIPP_ MR_ERR_BAD_MODULUS);
- MR_OUT
- return (mr_small)0;
- }
-
- zero(mr_mip->w6);
- zero(mr_mip->w15);
-
-/* set a small negative QNR (on the assumption that n is prime!) */
-/* These defaults can be over-ridden */
-
-/* Did you know that for p=2 mod 3, -3 is a QNR? */
-
- mr_mip->pmod8=remain(_MIPP_ n,8);
-
- switch (mr_mip->pmod8)
- {
- case 0:
- case 1:
- case 2:
- case 4:
- case 6:
- mr_mip->qnr=0; /* none defined */
- break;
- case 3:
- mr_mip->qnr=-1;
- break;
- case 5:
- mr_mip->qnr=-2;
- break;
- case 7:
- mr_mip->qnr=-1;
- break;
- }
- mr_mip->pmod9=remain(_MIPP_ n,9);
-
- mr_mip->NO_CARRY=FALSE;
- if (n->w[n->len-1]>>M4 < 5) mr_mip->NO_CARRY=TRUE;
-
-#ifdef MR_PENTIUM
-
-mr_mip->ACTIVE=FALSE;
-if (mr_mip->base!=0)
- if (MR_PENTIUM==n->len) mr_mip->ACTIVE=TRUE;
- if (MR_PENTIUM<0)
- {
- if (n->len<=(-MR_PENTIUM)) mr_mip->ACTIVE=TRUE;
- if (logb2(_MIPP_ n)%mr_mip->lg2b==0) mr_mip->ACTIVE=FALSE;
- }
-#endif
-
-#ifdef MR_DISABLE_MONTGOMERY
- mr_mip->MONTY=OFF;
-#else
- mr_mip->MONTY=ON;
-#endif
-
-#ifdef MR_COMBA
- mr_mip->ACTIVE=FALSE;
-
- if (MR_COMBA==n->len && mr_mip->base==mr_mip->base2)
- {
- mr_mip->ACTIVE=TRUE;
-#ifdef MR_SPECIAL
- mr_mip->MONTY=OFF; /* "special" modulus reduction */
-
-#endif /* implemented in mrcomba.c */
- }
-
-#endif
- convert(_MIPP_ 1,mr_mip->one);
- if (!mr_mip->MONTY)
- { /* Montgomery arithmetic is turned off */
- copy(n,mr_mip->modulus);
- mr_mip->ndash=0;
- MR_OUT
- return (mr_small)0;
- }
-
-#ifdef MR_KCM
-
-/* test for base==0 & n->len=MR_KCM.2^x */
-
- mr_mip->ACTIVE=FALSE;
- if (mr_mip->base==0)
- {
- nl=(int)n->len;
- while (nl>=MR_KCM)
- {
- if (nl==MR_KCM)
- {
- mr_mip->ACTIVE=TRUE;
- break;
- }
- if (nl%2!=0) break;
- nl/=2;
- }
- }
- if (mr_mip->ACTIVE)
- {
- mr_mip->w6->len=n->len+1;
- mr_mip->w6->w[n->len]=1;
- if (invmodp(_MIPP_ n,mr_mip->w6,mr_mip->w14)!=1)
- { /* problems */
- mr_berror(_MIPP_ MR_ERR_BAD_MODULUS);
- MR_OUT
- return (mr_small)0;
- }
- }
- else
- {
-#endif
- mr_mip->w6->len=2;
- mr_mip->w6->w[0]=0;
- mr_mip->w6->w[1]=1; /* w6 = base */
- mr_mip->w15->len=1;
- mr_mip->w15->w[0]=n->w[0]; /* w15 = n mod base */
- if (invmodp(_MIPP_ mr_mip->w15,mr_mip->w6,mr_mip->w14)!=1)
- { /* problems */
- mr_berror(_MIPP_ MR_ERR_BAD_MODULUS);
- MR_OUT
- return (mr_small)0;
- }
-#ifdef MR_KCM
- }
- copy(mr_mip->w14,mr_mip->big_ndash);
-#endif
-
- mr_mip->ndash=mr_mip->base-mr_mip->w14->w[0]; /* = N' mod b */
- copy(n,mr_mip->modulus);
- mr_mip->check=OFF;
- mr_shift(_MIPP_ mr_mip->modulus,(int)mr_mip->modulus->len,mr_mip->pR);
- mr_mip->check=ON;
-#ifdef MR_PENTIUM
-/* prime the FP stack */
- if (mr_mip->ACTIVE)
- {
- ndash=mr_mip->ndash;
- base=mr_mip->base;
- magic *=base;
- ASM
- {
- finit
- fldcw WORD PTR control
- fld QWORD PTR ndash
- fld1
- fld QWORD PTR base
- fdiv
- fld QWORD PTR magic
- }
- }
-#endif
- nres(_MIPP_ mr_mip->one,mr_mip->one);
- MR_OUT
-
- return mr_mip->ndash;
-}
-
-void nres(_MIPD_ big x,big y)
-{ /* convert x to n-residue format */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(81)
-
- if (size(mr_mip->modulus)==0)
- {
- mr_berror(_MIPP_ MR_ERR_NO_MODULUS);
- MR_OUT
- return;
- }
- copy(x,y);
- divide(_MIPP_ y,mr_mip->modulus,mr_mip->modulus);
- if (size(y)<0) add(_MIPP_ y,mr_mip->modulus,y);
- if (!mr_mip->MONTY)
- {
- MR_OUT
- return;
- }
- mr_mip->check=OFF;
-
- mr_shift(_MIPP_ y,(int)mr_mip->modulus->len,mr_mip->w0);
- divide(_MIPP_ mr_mip->w0,mr_mip->modulus,mr_mip->modulus);
- mr_mip->check=ON;
- copy(mr_mip->w0,y);
-
- MR_OUT
-}
-
-void redc(_MIPD_ big x,big y)
-{ /* Montgomery's REDC function p. 520 */
- /* also used to convert n-residues back to normal form */
- mr_small carry,delay_carry,m,ndash,*w0g,*mg;
-
-#ifdef MR_ITANIUM
- mr_small tm;
-#endif
-#ifdef MR_WIN64
- mr_small tm,tr;
-#endif
- int i,j,rn,rn2;
- big w0,modulus;
-#ifdef MR_NOASM
- union doubleword dble;
- mr_large dbled,ldres;
-#endif
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(82)
-
- w0=mr_mip->w0; /* get these into local variables (for inline assembly) */
- modulus=mr_mip->modulus;
- ndash=mr_mip->ndash;
-
- copy(x,w0);
- if (!mr_mip->MONTY)
- {
-/*#ifdef MR_CELL
- mod256(_MIPP_ w0,w0);
-#else */
- divide(_MIPP_ w0,modulus,modulus);
-/* #endif */
- copy(w0,y);
- MR_OUT
- return;
- }
- delay_carry=0;
- rn=(int)modulus->len;
- rn2=rn+rn;
-#ifndef MR_SIMPLE_BASE
- if (mr_mip->base==0)
- {
-#endif
-#ifndef MR_NOFULLWIDTH
- mg=modulus->w;
- w0g=w0->w;
- for (i=0;iw[i],ndash,0,&m); Note that after this time */
- m=ndash*w0->w[i];
- carry=0; /* around the loop, w0[i]=0 */
-
- for (j=0;jw[j]+carry+w0->w[i+j];
- w0->w[i+j]=dble.h[MR_BOT];
- carry=dble.h[MR_TOP];
-#else
- muldvd2(m,modulus->w[j],&carry,&w0->w[i+j]);
-#endif
- }
- w0->w[rn+i]+=delay_carry;
- if (w0->w[rn+i]w[rn+i]+=carry;
- if (w0->w[rn+i]w[i],ndash,0,mr_mip->base,mr_mip->inverse_base,&m);
-#else
- muldiv(w0->w[i],ndash,0,mr_mip->base,&m);
-#endif
- carry=0;
- for (j=0;jw[j]+carry+w0->w[i+j];
-#ifdef MR_FP_ROUNDING
- carry=(mr_small)MR_LROUND(dbled*mr_mip->inverse_base);
-#else
-#ifndef MR_FP
- if (mr_mip->base==mr_mip->base2)
- carry=(mr_small)(dbled>>mr_mip->lg2b);
- else
-#endif
- carry=(mr_small)MR_LROUND(dbled/mr_mip->base);
-#endif
- w0->w[i+j]=(mr_small)(dbled-(mr_large)carry*mr_mip->base);
-#else
-#ifdef MR_FP_ROUNDING
- carry=imuldiv(modulus->w[j],m,w0->w[i+j]+carry,mr_mip->base,mr_mip->inverse_base,&w0->w[i+j]);
-#else
- carry=muldiv(modulus->w[j],m,w0->w[i+j]+carry,mr_mip->base,&w0->w[i+j]);
-#endif
-#endif
- }
- w0->w[rn+i]+=(delay_carry+carry);
- delay_carry=0;
- if (w0->w[rn+i]>=mr_mip->base)
- {
- w0->w[rn+i]-=mr_mip->base;
- delay_carry=1;
- }
- }
-#endif
- w0->w[rn2]=delay_carry;
- w0->len=rn2+1;
- mr_shift(_MIPP_ w0,(-rn),w0);
- mr_lzero(w0);
-
- if (mr_compare(w0,modulus)>=0) mr_psub(_MIPP_ w0,modulus,w0);
- copy(w0,y);
- MR_OUT
-}
-
-/* "Complex" method for ZZn2 squaring */
-
-void nres_complex(_MIPD_ big a,big b,big r,big i)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
- MR_IN(225)
-
- if (mr_mip->NO_CARRY && mr_mip->qnr==-1)
- { /* if modulus is small enough we can ignore carries, and use simple addition and subtraction */
- /* recall that Montgomery reduction can cope as long as product is less than pR */
-#ifdef MR_COMBA
-#ifdef MR_COUNT_OPS
-fpa+=3;
-#endif
- if (mr_mip->ACTIVE)
- {
- comba_add(a,b,mr_mip->w1);
- comba_add(a,mr_mip->modulus,mr_mip->w2); /* a-b is p+a-b */
- comba_sub(mr_mip->w2,b,mr_mip->w2);
- comba_add(a,a,r);
- }
- else
- {
-#endif
- mr_padd(_MIPP_ a,b,mr_mip->w1);
- mr_padd(_MIPP_ a,mr_mip->modulus,mr_mip->w2);
- mr_psub(_MIPP_ mr_mip->w2,b,mr_mip->w2);
- mr_padd(_MIPP_ a,a,r);
-#ifdef MR_COMBA
- }
-#endif
- nres_modmult(_MIPP_ r,b,i);
- nres_modmult(_MIPP_ mr_mip->w1,mr_mip->w2,r);
- }
- else
- {
- nres_modadd(_MIPP_ a,b,mr_mip->w1);
- nres_modsub(_MIPP_ a,b,mr_mip->w2);
-
- if (mr_mip->qnr==-2)
- nres_modsub(_MIPP_ mr_mip->w2,b,mr_mip->w2);
-
- nres_modmult(_MIPP_ a,b,i);
- nres_modmult(_MIPP_ mr_mip->w1,mr_mip->w2,r);
-
- if (mr_mip->qnr==-2)
- nres_modadd(_MIPP_ r,i,r);
-
- nres_modadd(_MIPP_ i,i,i);
- }
- MR_OUT
-}
-
-#ifndef MR_NO_LAZY_REDUCTION
-
-/*
-
-Lazy reduction technique for zzn2 multiplication - competitive if Reduction is more
-expensive that Multiplication. This is true for pairing-based crypto. Note that
-Lazy reduction can also be used with Karatsuba! Uses w1, w2, w5, and w6.
-
-Reduction poly is X^2-D=0
-
-(a0+a1.X).(b0+b1.X) = (a0.b0 + D.a1.b1) + (a1.b0+a0.b1).X
-
-Karatsuba
-
- (a0.b0+D.a1.b1) + ((a0+a1)(b0+b1) - a0.b0 - a1.b1).X
-*/
-
-void nres_lazy(_MIPD_ big a0,big a1,big b0,big b1,big r,big i)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- mr_mip->check=OFF;
-#ifdef MR_COUNT_OPS
-fpc+=3;
-fpa+=5;
-if (mr_mip->qnr==-2) fpa++;
-#endif
-
-#ifdef MR_COMBA
- if (mr_mip->ACTIVE)
- {
- comba_mult(a0,b0,mr_mip->w0);
- comba_mult(a1,b1,mr_mip->w5);
- }
- else
- {
-#endif
-#ifdef MR_KCM
- if (mr_mip->ACTIVE)
- {
- kcm_mul(_MIPP_ a1,b1,mr_mip->w5); /* this destroys w0! */
- kcm_mul(_MIPP_ a0,b0,mr_mip->w0);
- }
- else
- {
-#endif
- MR_IN(151)
- multiply(_MIPP_ a0,b0,mr_mip->w0);
- multiply(_MIPP_ a1,b1,mr_mip->w5);
-#ifdef MR_COMBA
- }
-#endif
-#ifdef MR_KCM
- }
-#endif
-
- if (mr_mip->NO_CARRY && mr_mip->qnr==-1)
- { /* if modulus is small enough we can ignore carries, and use simple addition and subtraction */
-#ifdef MR_COMBA
-#ifdef MR_COUNT_OPS
-fpa+=2;
-#endif
- if (mr_mip->ACTIVE)
- {
- comba_double_add(mr_mip->w0,mr_mip->w5,mr_mip->w6);
- comba_add(a0,a1,mr_mip->w1);
- comba_add(b0,b1,mr_mip->w2);
- }
- else
- {
-#endif
- mr_padd(_MIPP_ mr_mip->w0,mr_mip->w5,mr_mip->w6);
- mr_padd(_MIPP_ a0,a1,mr_mip->w1);
- mr_padd(_MIPP_ b0,b1,mr_mip->w2);
-#ifdef MR_COMBA
- }
-#endif
- }
- else
- {
- nres_double_modadd(_MIPP_ mr_mip->w0,mr_mip->w5,mr_mip->w6); /* w6 = a0.b0+a1.b1 */
- if (mr_mip->qnr==-2)
- nres_double_modadd(_MIPP_ mr_mip->w5,mr_mip->w5,mr_mip->w5);
- nres_modadd(_MIPP_ a0,a1,mr_mip->w1);
- nres_modadd(_MIPP_ b0,b1,mr_mip->w2);
- }
- nres_double_modsub(_MIPP_ mr_mip->w0,mr_mip->w5,mr_mip->w0); /* r = a0.b0+D.a1.b1 */
-
-#ifdef MR_COMBA
- if (mr_mip->ACTIVE)
- {
- comba_redc(_MIPP_ mr_mip->w0,r);
- comba_mult(mr_mip->w1,mr_mip->w2,mr_mip->w0);
- }
- else
- {
-#endif
-#ifdef MR_KCM
- if (mr_mip->ACTIVE)
- {
- kcm_redc(_MIPP_ mr_mip->w0,r);
- kcm_mul(_MIPP_ mr_mip->w1,mr_mip->w2,mr_mip->w0);
- }
- else
- {
-#endif
- redc(_MIPP_ mr_mip->w0,r);
- multiply(_MIPP_ mr_mip->w1,mr_mip->w2,mr_mip->w0); /* w0=(a0+a1)*(b0+b1) */
-#ifdef MR_COMBA
- }
-#endif
-#ifdef MR_KCM
- }
-#endif
-
- if (mr_mip->NO_CARRY && mr_mip->qnr==-1)
- {
-#ifdef MR_COMBA
- if (mr_mip->ACTIVE)
- comba_double_sub(mr_mip->w0,mr_mip->w6,mr_mip->w0);
- else
-#endif
- mr_psub(_MIPP_ mr_mip->w0,mr_mip->w6,mr_mip->w0);
- }
- else
- nres_double_modsub(_MIPP_ mr_mip->w0,mr_mip->w6,mr_mip->w0); /* (a0+a1)*(b0+b1) - w6 */
-
-#ifdef MR_COMBA
- if (mr_mip->ACTIVE)
- {
- comba_redc(_MIPP_ mr_mip->w0,i);
- }
- else
- {
-#endif
-#ifdef MR_KCM
- if (mr_mip->ACTIVE)
- {
- kcm_redc(_MIPP_ mr_mip->w0,i);
- }
- else
- {
-#endif
- redc(_MIPP_ mr_mip->w0,i);
- MR_OUT
-#ifdef MR_COMBA
- }
-#endif
-#ifdef MR_KCM
- }
-#endif
-
- mr_mip->check=ON;
-
-}
-
-#endif
-
-#ifndef MR_STATIC
-
-void nres_dotprod(_MIPD_ int n,big *x,big *y,big w)
-{
- int i;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- if (mr_mip->ERNUM) return;
- MR_IN(120)
- mr_mip->check=OFF;
- zero(mr_mip->w7);
- for (i=0;iw0);
- mr_padd(_MIPP_ mr_mip->w7,mr_mip->w0,mr_mip->w7);
- }
- copy(mr_mip->pR,mr_mip->w6);
- /* w6 = p.R */
- divide(_MIPP_ mr_mip->w7,mr_mip->w6,mr_mip->w6);
- redc(_MIPP_ mr_mip->w7,w);
-
- mr_mip->check=ON;
- MR_OUT
-}
-
-#endif
-
-void nres_negate(_MIPD_ big x, big w)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (size(x)==0)
- {
- zero(w);
- return;
- }
-#ifdef MR_COMBA
- if (mr_mip->ACTIVE)
- {
- comba_negate(_MIPP_ x,w);
- return;
- }
- else
- {
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(92)
- mr_psub(_MIPP_ mr_mip->modulus,x,w);
- MR_OUT
-
-#ifdef MR_COMBA
- }
-#endif
-
-}
-
-void nres_div2(_MIPD_ big x,big w)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- MR_IN(198)
- copy(x,mr_mip->w1);
- if (remain(_MIPP_ mr_mip->w1,2)!=0)
- add(_MIPP_ mr_mip->w1,mr_mip->modulus,mr_mip->w1);
- subdiv(_MIPP_ mr_mip->w1,2,mr_mip->w1);
- copy(mr_mip->w1,w);
-
- MR_OUT
-}
-
-void nres_div3(_MIPD_ big x,big w)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- MR_IN(199)
- copy(x,mr_mip->w1);
- while (remain(_MIPP_ mr_mip->w1,3)!=0)
- add(_MIPP_ mr_mip->w1,mr_mip->modulus,mr_mip->w1);
- subdiv(_MIPP_ mr_mip->w1,3,mr_mip->w1);
- copy(mr_mip->w1,w);
-
- MR_OUT
-}
-
-void nres_div5(_MIPD_ big x,big w)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- MR_IN(208)
- copy(x,mr_mip->w1);
- while (remain(_MIPP_ mr_mip->w1,5)!=0)
- add(_MIPP_ mr_mip->w1,mr_mip->modulus,mr_mip->w1);
- subdiv(_MIPP_ mr_mip->w1,5,mr_mip->w1);
- copy(mr_mip->w1,w);
-
- MR_OUT
-}
-
-/* mod pR addition and subtraction */
-#ifndef MR_NO_LAZY_REDUCTION
-
-void nres_double_modadd(_MIPD_ big x,big y,big w)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-#ifdef MR_COMBA
-
- if (mr_mip->ACTIVE)
- {
- comba_double_modadd(_MIPP_ x,y,w);
- return;
- }
- else
- {
-#endif
-
- if (mr_mip->ERNUM) return;
- MR_IN(153)
-
- mr_padd(_MIPP_ x,y,w);
- if (mr_compare(w,mr_mip->pR)>=0)
- mr_psub(_MIPP_ w,mr_mip->pR,w);
-
- MR_OUT
-#ifdef MR_COMBA
- }
-#endif
-}
-
-void nres_double_modsub(_MIPD_ big x,big y,big w)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-#ifdef MR_COMBA
-
- if (mr_mip->ACTIVE)
- {
- comba_double_modsub(_MIPP_ x,y,w);
- return;
- }
- else
- {
-#endif
-
- if (mr_mip->ERNUM) return;
- MR_IN(154)
-
- if (mr_compare(x,y)>=0)
- mr_psub(_MIPP_ x,y,w);
- else
- {
- mr_psub(_MIPP_ y,x,w);
- mr_psub(_MIPP_ mr_mip->pR,w,w);
- }
-
- MR_OUT
-#ifdef MR_COMBA
- }
-#endif
-}
-
-#endif
-
-void nres_modadd(_MIPD_ big x,big y,big w)
-{ /* modular addition */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-#ifdef MR_COUNT_OPS
-fpa++;
-#endif
-#ifdef MR_COMBA
-
- if (mr_mip->ACTIVE)
- {
- comba_modadd(_MIPP_ x,y,w);
- return;
- }
- else
- {
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(90)
- mr_padd(_MIPP_ x,y,w);
- if (mr_compare(w,mr_mip->modulus)>=0) mr_psub(_MIPP_ w,mr_mip->modulus,w);
-
- MR_OUT
-#ifdef MR_COMBA
- }
-#endif
-}
-
-void nres_modsub(_MIPD_ big x,big y,big w)
-{ /* modular subtraction */
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-#ifdef MR_COUNT_OPS
-fpa++;
-#endif
-#ifdef MR_COMBA
- if (mr_mip->ACTIVE)
- {
- comba_modsub(_MIPP_ x,y,w);
- return;
- }
- else
- {
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(91)
-
- if (mr_compare(x,y)>=0)
- mr_psub(_MIPP_ x,y,w);
- else
- {
- mr_psub(_MIPP_ y,x,w);
- mr_psub(_MIPP_ mr_mip->modulus,w,w);
- }
-
- MR_OUT
-#ifdef MR_COMBA
- }
-#endif
-
-}
-
-int nres_moddiv(_MIPD_ big x,big y,big w)
-{ /* Modular division using n-residues w=x/y mod n */
- int gcd;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return 0;
-
- MR_IN(85)
-
- if (x==y)
- { /* Illegal parameter usage */
- mr_berror(_MIPP_ MR_ERR_BAD_PARAMETERS);
- MR_OUT
-
- return 0;
- }
- redc(_MIPP_ y,mr_mip->w6);
- gcd=invmodp(_MIPP_ mr_mip->w6,mr_mip->modulus,mr_mip->w6);
-
- if (gcd!=1) zero(w); /* fails silently and returns 0 */
- else
- {
- nres(_MIPP_ mr_mip->w6,mr_mip->w6);
- nres_modmult(_MIPP_ x,mr_mip->w6,w);
- /* mad(_MIPP_ x,mr_mip->w6,x,mr_mip->modulus,mr_mip->modulus,w); */
- }
- MR_OUT
- return gcd;
-}
-
-void nres_premult(_MIPD_ big x,int k,big w)
-{ /* multiply n-residue by small ordinary integer */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- int sign=0;
- if (k==0)
- {
- zero(w);
- return;
- }
- if (k<0)
- {
- k=-k;
- sign=1;
- }
- if (mr_mip->ERNUM) return;
-
- MR_IN(102)
-
- if (k<=6)
- {
- switch (k)
- {
- case 1: copy(x,w);
- break;
- case 2: nres_modadd(_MIPP_ x,x,w);
- break;
- case 3:
- nres_modadd(_MIPP_ x,x,mr_mip->w0);
- nres_modadd(_MIPP_ x,mr_mip->w0,w);
- break;
- case 4:
- nres_modadd(_MIPP_ x,x,w);
- nres_modadd(_MIPP_ w,w,w);
- break;
- case 5:
- nres_modadd(_MIPP_ x,x,mr_mip->w0);
- nres_modadd(_MIPP_ mr_mip->w0,mr_mip->w0,mr_mip->w0);
- nres_modadd(_MIPP_ x,mr_mip->w0,w);
- break;
- case 6:
- nres_modadd(_MIPP_ x,x,w);
- nres_modadd(_MIPP_ w,w,mr_mip->w0);
- nres_modadd(_MIPP_ w,mr_mip->w0,w);
- break;
- }
- if (sign==1) nres_negate(_MIPP_ w,w);
- MR_OUT
- return;
- }
-
- mr_pmul(_MIPP_ x,(mr_small)k,mr_mip->w0);
-#ifdef MR_COMBA
-#ifdef MR_SPECIAL
- comba_redc(_MIPP_ mr_mip->w0,w);
-#else
- divide(_MIPP_ mr_mip->w0,mr_mip->modulus,mr_mip->modulus);
- copy(mr_mip->w0,w);
-#endif
-#else
- divide(_MIPP_ mr_mip->w0,mr_mip->modulus,mr_mip->modulus);
- copy(mr_mip->w0,w);
-#endif
-
- if (sign==1) nres_negate(_MIPP_ w,w);
-
- MR_OUT
-}
-
-void nres_modmult(_MIPD_ big x,big y,big w)
-{ /* Modular multiplication using n-residues w=x*y mod n */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if ((x==NULL || x->len==0) && x==w) return;
- if ((y==NULL || y->len==0) && y==w) return;
- if (y==NULL || x==NULL || x->len==0 || y->len==0)
- {
- zero(w);
- return;
- }
-#ifdef MR_COUNT_OPS
-fpc++;
-#endif
-#ifdef MR_COMBA
- if (mr_mip->ACTIVE)
- {
- if (x==y) comba_square(x,mr_mip->w0);
- else comba_mult(x,y,mr_mip->w0);
- comba_redc(_MIPP_ mr_mip->w0,w);
- }
- else
- {
-#endif
-#ifdef MR_KCM
- if (mr_mip->ACTIVE)
- {
- if (x==y) kcm_sqr(_MIPP_ x,mr_mip->w0);
- else kcm_mul(_MIPP_ x,y,mr_mip->w0);
- kcm_redc(_MIPP_ mr_mip->w0,w);
- }
- else
- {
-#endif
-#ifdef MR_PENTIUM
- if (mr_mip->ACTIVE)
- {
- if (x==y) fastmodsquare(_MIPP_ x,w);
- else fastmodmult(_MIPP_ x,y,w);
- }
- else
- {
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(83)
-
- mr_mip->check=OFF;
- multiply(_MIPP_ x,y,mr_mip->w0);
- redc(_MIPP_ mr_mip->w0,w);
- mr_mip->check=ON;
- MR_OUT
-#ifdef MR_COMBA
-}
-#endif
-#ifdef MR_KCM
-}
-#endif
-#ifdef MR_PENTIUM
-}
-#endif
-
-}
-
-/* Montgomery's trick for finding multiple *
- * simultaneous modular inverses *
- * Based on the observation that *
- * 1/x = yz*(1/xyz) *
- * 1/y = xz*(1/xyz) *
- * 1/z = xy*(1/xyz) *
- * Why are all of Peter Montgomery's clever *
- * algorithms always described as "tricks" ??*/
-
-BOOL nres_double_inverse(_MIPD_ big x,big y,big w,big z)
-{ /* find y=1/x mod n and z=1/w mod n */
- /* 1/x = w/xw, and 1/w = x/xw */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- MR_IN(145)
-
- nres_modmult(_MIPP_ x,w,mr_mip->w6); /* xw */
-
- if (size(mr_mip->w6)==0)
- {
- mr_berror(_MIPP_ MR_ERR_DIV_BY_ZERO);
- MR_OUT
- return FALSE;
- }
- redc(_MIPP_ mr_mip->w6,mr_mip->w6);
- redc(_MIPP_ mr_mip->w6,mr_mip->w6);
- invmodp(_MIPP_ mr_mip->w6,mr_mip->modulus,mr_mip->w6);
-
- nres_modmult(_MIPP_ w,mr_mip->w6,mr_mip->w5);
- nres_modmult(_MIPP_ x,mr_mip->w6,z);
- copy(mr_mip->w5,y);
-
- MR_OUT
- return TRUE;
-}
-
-BOOL nres_multi_inverse(_MIPD_ int m,big *x,big *w)
-{ /* find w[i]=1/x[i] mod n, for i=0 to m-1 *
- * x and w MUST be distinct */
- int i;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (m==0) return TRUE;
- if (m<0) return FALSE;
- MR_IN(118)
-
- if (x==w)
- {
- mr_berror(_MIPP_ MR_ERR_BAD_PARAMETERS);
- MR_OUT
- return FALSE;
- }
-
- if (m==1)
- {
- copy(mr_mip->one,w[0]);
- nres_moddiv(_MIPP_ w[0],x[0],w[0]);
- MR_OUT
- return TRUE;
- }
-
- convert(_MIPP_ 1,w[0]);
- copy(x[0],w[1]);
- for (i=2;iw6); /* y=x[0]*x[1]*x[2]....x[m-1] */
- if (size(mr_mip->w6)==0)
- {
- mr_berror(_MIPP_ MR_ERR_DIV_BY_ZERO);
- MR_OUT
- return FALSE;
- }
-
- redc(_MIPP_ mr_mip->w6,mr_mip->w6);
- redc(_MIPP_ mr_mip->w6,mr_mip->w6);
-
- invmodp(_MIPP_ mr_mip->w6,mr_mip->modulus,mr_mip->w6);
-
-/* Now y=1/y */
-
- copy(x[m-1],mr_mip->w5);
- nres_modmult(_MIPP_ w[m-1],mr_mip->w6,w[m-1]);
-
- for (i=m-2;;i--)
- {
- if (i==0)
- {
- nres_modmult(_MIPP_ mr_mip->w5,mr_mip->w6,w[0]);
- break;
- }
- nres_modmult(_MIPP_ w[i],mr_mip->w5,w[i]);
- nres_modmult(_MIPP_ w[i],mr_mip->w6,w[i]);
- nres_modmult(_MIPP_ mr_mip->w5,x[i],mr_mip->w5);
- }
-
- MR_OUT
- return TRUE;
-}
-
-/* initialise elliptic curve */
-
-void ecurve_init(_MIPD_ big a,big b,big p,int type)
-{ /* Initialize the active ecurve *
- * Asize indicate size of A *
- * Bsize indicate size of B */
- int as;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return;
-
- MR_IN(93)
-
-#ifndef MR_NO_SS
- mr_mip->SS=FALSE; /* no special support for super-singular curves */
-#endif
-
- prepare_monty(_MIPP_ p);
-
- mr_mip->Asize=size(a);
- if (mr_abs(mr_mip->Asize)==MR_TOOBIG)
- {
- if (mr_mip->Asize>=0)
- { /* big positive number - check it isn't minus something small */
- copy(a,mr_mip->w1);
- divide(_MIPP_ mr_mip->w1,p,p);
- subtract(_MIPP_ p,mr_mip->w1,mr_mip->w1);
- as=size(mr_mip->w1);
- if (asAsize=-as;
- }
- }
- nres(_MIPP_ a,mr_mip->A);
-
- mr_mip->Bsize=size(b);
- if (mr_abs(mr_mip->Bsize)==MR_TOOBIG)
- {
- if (mr_mip->Bsize>=0)
- { /* big positive number - check it isn't minus something small */
- copy(b,mr_mip->w1);
- divide(_MIPP_ mr_mip->w1,p,p);
- subtract(_MIPP_ p,mr_mip->w1,mr_mip->w1);
- as=size(mr_mip->w1);
- if (asBsize=-as;
- }
- }
-
- nres(_MIPP_ b,mr_mip->B);
-#ifdef MR_EDWARDS
- mr_mip->coord=MR_PROJECTIVE; /* only type supported for Edwards curves */
-#else
-#ifndef MR_AFFINE_ONLY
- if (type==MR_BEST) mr_mip->coord=MR_PROJECTIVE;
- else mr_mip->coord=type;
-#else
- if (type==MR_PROJECTIVE)
- mr_berror(_MIPP_ MR_ERR_NOT_SUPPORTED);
-#endif
-#endif
- MR_OUT
- return;
-}
diff --git a/crypto/sm2/miracl/mrmuldv.c b/crypto/sm2/miracl/mrmuldv.c
deleted file mode 100644
index 0810017d..00000000
--- a/crypto/sm2/miracl/mrmuldv.c
+++ /dev/null
@@ -1,59 +0,0 @@
-/* Standard C version of mrmuldv.c */
-
-#include
-#include
-
-mr_small muldiv(mr_small a,mr_small b,mr_small c,mr_small m,mr_small *rp)
-{
- mr_small q;
- mr_large dble=(mr_large)a*b+c;
- q=(mr_small)MR_LROUND(dble/m);
- *rp=(mr_small)(dble-(mr_large)q*m);
- return q;
-}
-
-#ifdef MR_FP_ROUNDING
-
-mr_small imuldiv(mr_small a,mr_small b,mr_small c,mr_small m,mr_large im,mr_small *rp)
-{
- mr_small q;
- mr_large dble=(mr_large)a*b+c;
- q=(mr_small)MR_LROUND(dble*im);
- *rp=(mr_small)(dble-(mr_large)q*m);
- return q;
-}
-
-#endif
-
-
-#ifndef MR_NOFULLWIDTH
-
-mr_small muldvm(mr_small a,mr_small c,mr_small m,mr_small *rp)
-{
- mr_small q;
- union doubleword dble;
- dble.h[MR_BOT]=c;
- dble.h[MR_TOP]=a;
- q=(mr_small)(dble.d/m);
- *rp=(mr_small)(dble.d-(mr_large)q*m);
- return q;
-}
-
-mr_small muldvd(mr_small a,mr_small b,mr_small c,mr_small *rp)
-{
- union doubleword dble;
- dble.d=(mr_large)a*b+c;
- *rp=dble.h[MR_BOT];
- return dble.h[MR_TOP];
-}
-
-void muldvd2(mr_small a,mr_small b,mr_small *c,mr_small *rp)
-{
- union doubleword dble;
- dble.d=(mr_large)a*b+*c+*rp;
- *rp=dble.h[MR_BOT];
- *c=dble.h[MR_TOP];
-}
-
-#endif
-
diff --git a/crypto/sm2/miracl/mrsroot.c b/crypto/sm2/miracl/mrsroot.c
deleted file mode 100644
index ccf6d56b..00000000
--- a/crypto/sm2/miracl/mrsroot.c
+++ /dev/null
@@ -1,188 +0,0 @@
-
-/***************************************************************************
- *
-Copyright 2013 CertiVox IOM Ltd. *
- *
-This file is part of CertiVox MIRACL Crypto SDK. *
- *
-The CertiVox MIRACL Crypto SDK provides developers with an *
-extensive and efficient set of cryptographic functions. *
-For further information about its features and functionalities please *
-refer to http://www.certivox.com *
- *
-* The CertiVox MIRACL Crypto SDK is free software: you can *
- redistribute it and/or modify it under the terms of the *
- GNU Affero General Public License as published by the *
- Free Software Foundation, either version 3 of the License, *
- or (at your option) any later version. *
- *
-* The CertiVox MIRACL Crypto SDK is distributed in the hope *
- that it will be useful, but WITHOUT ANY WARRANTY; without even the *
- implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. *
- See the GNU Affero General Public License for more details. *
- *
-* You should have received a copy of the GNU Affero General Public *
- License along with CertiVox MIRACL Crypto SDK. *
- If not, see . *
- *
-You can be released from the requirements of the license by purchasing *
-a commercial license. Buying such a license is mandatory as soon as you *
-develop commercial activities involving the CertiVox MIRACL Crypto SDK *
-without disclosing the source code of your own applications, or shipping *
-the CertiVox MIRACL Crypto SDK with a closed source product. *
- *
-***************************************************************************/
-/*
- * MIRACL method for modular square root
- * mrsroot.c
- *
- * Siguna Mueller's O(lg(p)^3) algorithm, Designs Codes and Cryptography, 2004
- *
- * This is a little slower for p=1 mod 4 primes, but its not time critical, and
- * more importantly it doesn't pull in the large powmod code into elliptic curve programs
- * It does require code from mrjack.c and mrlucas.c
- *
- * If p=3 mod 4, then sqrt(a)=a^[(p+1)/4] mod p. Note that for many elliptic curves
- * (p+1)/4 has very low hamming weight.
- *
- * (was sqrt(a) = V_{(p+1)/4}(a+1/a,1)/(1+1/a))
- *
- * Mueller's method is also very simple, uses very little memory, and it works just fine for p=1 mod 8 primes
- * (for example the "annoying" NIST modulus 2^224-2^96+1)
- * Also doesn't waste time on non-squares, as a jacobi test is done first
- *
- * If you know that the prime is 3 mod 4, and you know that x is almost certainly a QR
- * then the jacobi-dependent code can be deleted with some space savings.
- *
- * NOTE - IF p IS NOT PRIME, THIS CODE WILL FAIL SILENTLY!
- *
- */
-
-#include
-#include
-
-BOOL nres_sqroot(_MIPD_ big x,big w)
-{ /* w=sqrt(x) mod p. This depends on p being prime! */
- int t,js;
-
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return FALSE;
-
- copy(x,w);
- if (size(w)==0) return TRUE;
-
- MR_IN(100)
-
- redc(_MIPP_ w,w); /* get it back into normal form */
-
- if (size(w)==1) /* square root of 1 is 1 */
- {
- nres(_MIPP_ w,w);
- MR_OUT
- return TRUE;
- }
-
- if (size(w)==4) /* square root of 4 is 2 */
- {
- convert(_MIPP_ 2,w);
- nres(_MIPP_ w,w);
- MR_OUT
- return TRUE;
- }
-
- if (jack(_MIPP_ w,mr_mip->modulus)!=1)
- { /* Jacobi test */
- zero(w);
- MR_OUT
- return FALSE;
- }
-
- js=mr_mip->pmod8%4-2; /* 1 mod 4 or 3 mod 4 prime? */
-
- incr(_MIPP_ mr_mip->modulus,js,mr_mip->w10);
- subdiv(_MIPP_ mr_mip->w10,4,mr_mip->w10); /* (p+/-1)/4 */
-
- if (js==1)
- { /* 3 mod 4 primes - do a quick and dirty sqrt(x)=x^(p+1)/4 mod p */
- nres(_MIPP_ w,mr_mip->w2);
- copy(mr_mip->one,w);
- forever
- { /* Simple Right-to-Left exponentiation */
-
- if (mr_mip->user!=NULL) (*mr_mip->user)();
- if (subdiv(_MIPP_ mr_mip->w10,2,mr_mip->w10)!=0)
- nres_modmult(_MIPP_ w,mr_mip->w2,w);
- if (mr_mip->ERNUM || size(mr_mip->w10)==0) break;
- nres_modmult(_MIPP_ mr_mip->w2,mr_mip->w2,mr_mip->w2);
- }
-
- /* nres_moddiv(_MIPP_ mr_mip->one,w,mr_mip->w11);
- nres_modadd(_MIPP_ mr_mip->w11,w,mr_mip->w3);
- nres_lucas(_MIPP_ mr_mip->w3,mr_mip->w10,w,w);
- nres_modadd(_MIPP_ mr_mip->w11,mr_mip->one,mr_mip->w11);
- nres_moddiv(_MIPP_ w,mr_mip->w11,w); */
- }
- else
- { /* 1 mod 4 primes */
- for (t=1; ;t++)
- { /* t=1.5 on average */
- if (t==1) copy(w,mr_mip->w4);
- else
- {
- premult(_MIPP_ w,t,mr_mip->w4);
- divide(_MIPP_ mr_mip->w4,mr_mip->modulus,mr_mip->modulus);
- premult(_MIPP_ mr_mip->w4,t,mr_mip->w4);
- divide(_MIPP_ mr_mip->w4,mr_mip->modulus,mr_mip->modulus);
- }
-
- decr(_MIPP_ mr_mip->w4,4,mr_mip->w1);
- if (jack(_MIPP_ mr_mip->w1,mr_mip->modulus)==js) break;
- if (mr_mip->ERNUM) break;
- }
-
- decr(_MIPP_ mr_mip->w4,2,mr_mip->w3);
- nres(_MIPP_ mr_mip->w3,mr_mip->w3);
- nres_lucas(_MIPP_ mr_mip->w3,mr_mip->w10,w,w); /* heavy lifting done here */
- if (t!=1)
- {
- convert(_MIPP_ t,mr_mip->w11);
- nres(_MIPP_ mr_mip->w11,mr_mip->w11);
- nres_moddiv(_MIPP_ w,mr_mip->w11,w);
- }
- }
-
- MR_OUT
- return TRUE;
-}
-
-BOOL sqroot(_MIPD_ big x,big p,big w)
-{ /* w = sqrt(x) mod p */
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (mr_mip->ERNUM) return FALSE;
-
- MR_IN(101)
-
- if (subdivisible(_MIPP_ p,2))
- { /* p must be odd */
- zero(w);
- MR_OUT
- return FALSE;
- }
-
- prepare_monty(_MIPP_ p);
- nres(_MIPP_ x,w);
- if (nres_sqroot(_MIPP_ w,w))
- {
- redc(_MIPP_ w,w);
- MR_OUT
- return TRUE;
- }
-
- zero(w);
- MR_OUT
- return FALSE;
-}
diff --git a/crypto/sm2/miracl/mrxgcd.c b/crypto/sm2/miracl/mrxgcd.c
deleted file mode 100644
index 437f6e97..00000000
--- a/crypto/sm2/miracl/mrxgcd.c
+++ /dev/null
@@ -1,495 +0,0 @@
-
-/***************************************************************************
- *
-Copyright 2013 CertiVox IOM Ltd. *
- *
-This file is part of CertiVox MIRACL Crypto SDK. *
- *
-The CertiVox MIRACL Crypto SDK provides developers with an *
-extensive and efficient set of cryptographic functions. *
-For further information about its features and functionalities please *
-refer to http://www.certivox.com *
- *
-* The CertiVox MIRACL Crypto SDK is free software: you can *
- redistribute it and/or modify it under the terms of the *
- GNU Affero General Public License as published by the *
- Free Software Foundation, either version 3 of the License, *
- or (at your option) any later version. *
- *
-* The CertiVox MIRACL Crypto SDK is distributed in the hope *
- that it will be useful, but WITHOUT ANY WARRANTY; without even the *
- implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. *
- See the GNU Affero General Public License for more details. *
- *
-* You should have received a copy of the GNU Affero General Public *
- License along with CertiVox MIRACL Crypto SDK. *
- If not, see . *
- *
-You can be released from the requirements of the license by purchasing *
-a commercial license. Buying such a license is mandatory as soon as you *
-develop commercial activities involving the CertiVox MIRACL Crypto SDK *
-without disclosing the source code of your own applications, or shipping *
-the CertiVox MIRACL Crypto SDK with a closed source product. *
- *
-***************************************************************************/
-/*
- * MIRACL Extended Greatest Common Divisor module.
- * mrxgcd.c
- */
-
-#include
-
-#ifdef MR_FP
-#include
-#endif
-
-#ifdef MR_COUNT_OPS
-extern int fpx;
-#endif
-
-#ifndef MR_USE_BINARY_XGCD
-
-#ifdef mr_dltype
-
-static mr_small qdiv(mr_large u,mr_large v)
-{ /* fast division - small quotient expected. */
- mr_large lq,x=u;
-#ifdef MR_FP
- mr_small dres;
-#endif
- x-=v;
- if (x=MAXBASE) return 0;
- return (mr_small)lq;
-}
-
-#else
-
-static mr_small qdiv(mr_small u,mr_small v)
-{ /* fast division - small quotient expected */
- mr_small x=u;
- x-=v;
- if (xERNUM) return 0;
-
- MR_IN(30)
-
-#ifdef MR_COUNT_OPS
- fpx++;
-#endif
-
- copy(x,mr_mip->w1);
- copy(y,mr_mip->w2);
- s=exsign(mr_mip->w1);
- insign(PLUS,mr_mip->w1);
- insign(PLUS,mr_mip->w2);
- convert(_MIPP_ 1,mr_mip->w3);
- zero(mr_mip->w4);
- last=FALSE;
- a=b=c=d=0;
- iter=0;
-
- while (size(mr_mip->w2)!=0)
- {
- if (b==0)
- { /* update mr_mip->w1 and mr_mip->w2 */
-
- divide(_MIPP_ mr_mip->w1,mr_mip->w2,mr_mip->w5);
- t=mr_mip->w1,mr_mip->w1=mr_mip->w2,mr_mip->w2=t; /* swap(mr_mip->w1,mr_mip->w2) */
- multiply(_MIPP_ mr_mip->w4,mr_mip->w5,mr_mip->w0);
- add(_MIPP_ mr_mip->w3,mr_mip->w0,mr_mip->w3);
- t=mr_mip->w3,mr_mip->w3=mr_mip->w4,mr_mip->w4=t; /* swap(xd,yd) */
- iter++;
-
- }
- else
- {
-
- /* printf("a= %I64u b= %I64u c= %I64u d= %I64u \n",a,b,c,d); */
-
- mr_pmul(_MIPP_ mr_mip->w1,c,mr_mip->w5); /* c*w1 */
- mr_pmul(_MIPP_ mr_mip->w1,a,mr_mip->w1); /* a*w1 */
- mr_pmul(_MIPP_ mr_mip->w2,b,mr_mip->w0); /* b*w2 */
- mr_pmul(_MIPP_ mr_mip->w2,d,mr_mip->w2); /* d*w2 */
-
- if (!dplus)
- {
- mr_psub(_MIPP_ mr_mip->w0,mr_mip->w1,mr_mip->w1); /* b*w2-a*w1 */
- mr_psub(_MIPP_ mr_mip->w5,mr_mip->w2,mr_mip->w2); /* c*w1-d*w2 */
- }
- else
- {
- mr_psub(_MIPP_ mr_mip->w1,mr_mip->w0,mr_mip->w1); /* a*w1-b*w2 */
- mr_psub(_MIPP_ mr_mip->w2,mr_mip->w5,mr_mip->w2); /* d*w2-c*w1 */
- }
- mr_pmul(_MIPP_ mr_mip->w3,c,mr_mip->w5);
- mr_pmul(_MIPP_ mr_mip->w3,a,mr_mip->w3);
- mr_pmul(_MIPP_ mr_mip->w4,b,mr_mip->w0);
- mr_pmul(_MIPP_ mr_mip->w4,d,mr_mip->w4);
-
- if (a==0) copy(mr_mip->w0,mr_mip->w3);
- else mr_padd(_MIPP_ mr_mip->w3,mr_mip->w0,mr_mip->w3);
- mr_padd(_MIPP_ mr_mip->w4,mr_mip->w5,mr_mip->w4);
- }
- if (mr_mip->ERNUM || size(mr_mip->w2)==0) break;
-
-
- n=(int)mr_mip->w1->len;
- if (n==1)
- {
- last=TRUE;
- u=mr_mip->w1->w[0];
- v=mr_mip->w2->w[0];
- }
- else
- {
- m=mr_mip->w1->w[n-1]+1;
-#ifndef MR_SIMPLE_BASE
- if (mr_mip->base==0)
- {
-#endif
-#ifndef MR_NOFULLWIDTH
-#ifdef mr_dltype
- /* use double length type if available */
- if (n>2 && m!=0)
- { /* squeeze out as much significance as possible */
- uu.h[MR_TOP]=muldvm(mr_mip->w1->w[n-1],mr_mip->w1->w[n-2],m,&sr);
- uu.h[MR_BOT]=muldvm(sr,mr_mip->w1->w[n-3],m,&sr);
- vv.h[MR_TOP]=muldvm(mr_mip->w2->w[n-1],mr_mip->w2->w[n-2],m,&sr);
- vv.h[MR_BOT]=muldvm(sr,mr_mip->w2->w[n-3],m,&sr);
- }
- else
- {
- uu.h[MR_TOP]=mr_mip->w1->w[n-1];
- uu.h[MR_BOT]=mr_mip->w1->w[n-2];
- vv.h[MR_TOP]=mr_mip->w2->w[n-1];
- vv.h[MR_BOT]=mr_mip->w2->w[n-2];
- if (n==2) last=TRUE;
- }
-
- u=uu.d;
- v=vv.d;
-#else
- if (m==0)
- {
- u=mr_mip->w1->w[n-1];
- v=mr_mip->w2->w[n-1];
- }
- else
- {
- u=muldvm(mr_mip->w1->w[n-1],mr_mip->w1->w[n-2],m,&sr);
- v=muldvm(mr_mip->w2->w[n-1],mr_mip->w2->w[n-2],m,&sr);
- }
-#endif
-#endif
-#ifndef MR_SIMPLE_BASE
- }
- else
- {
-#ifdef mr_dltype
- if (n>2)
- { /* squeeze out as much significance as possible */
- u=muldiv(mr_mip->w1->w[n-1],mr_mip->base,mr_mip->w1->w[n-2],m,&sr);
- u=u*mr_mip->base+muldiv(sr,mr_mip->base,mr_mip->w1->w[n-3],m,&sr);
- v=muldiv(mr_mip->w2->w[n-1],mr_mip->base,mr_mip->w2->w[n-2],m,&sr);
- v=v*mr_mip->base+muldiv(sr,mr_mip->base,mr_mip->w2->w[n-3],m,&sr);
- }
- else
- {
- u=(mr_large)mr_mip->base*mr_mip->w1->w[n-1]+mr_mip->w1->w[n-2];
- v=(mr_large)mr_mip->base*mr_mip->w2->w[n-1]+mr_mip->w2->w[n-2];
- last=TRUE;
- }
-#else
- u=muldiv(mr_mip->w1->w[n-1],mr_mip->base,mr_mip->w1->w[n-2],m,&sr);
- v=muldiv(mr_mip->w2->w[n-1],mr_mip->base,mr_mip->w2->w[n-2],m,&sr);
-#endif
- }
-#endif
- }
-
- dplus=TRUE;
- a=1; b=0; c=0; d=1;
-
- forever
- { /* work only with most significant piece */
- if (last)
- {
- if (v==0) break;
- q=qdiv(u,v);
- if (q==0) break;
- }
- else
- {
- if (dplus)
- {
- if ((mr_small)(v-c)==0 || (mr_small)(v+d)==0) break;
-
- q=qdiv(u+a,v-c);
-
- if (q==0) break;
-
- if (q!=qdiv(u-b,v+d)) break;
- }
- else
- {
- if ((mr_small)(v+c)==0 || (mr_small)(v-d)==0) break;
- q=qdiv(u-a,v+c);
- if (q==0) break;
- if (q!=qdiv(u+b,v-d)) break;
- }
- }
-
- if (q==1)
- {
- if ((mr_small)(b+d) >= MAXBASE) break;
- r=a+c; a=c; c=r;
- r=b+d; b=d; d=r;
- lr=u-v; u=v; v=lr;
- }
- else
- {
- if (q>=MR_DIV(MAXBASE-b,d)) break;
- r=a+q*c; a=c; c=r;
- r=b+q*d; b=d; d=r;
- lr=u-q*v; u=v; v=lr;
- }
- iter++;
- dplus=!dplus;
- }
- iter%=2;
-
- }
-
- if (s==MINUS) iter++;
- if (iter%2==1) subtract(_MIPP_ y,mr_mip->w3,mr_mip->w3);
-
- if (xd!=yd)
- {
- negify(x,mr_mip->w2);
- mad(_MIPP_ mr_mip->w2,mr_mip->w3,mr_mip->w1,y,mr_mip->w4,mr_mip->w4);
- copy(mr_mip->w4,yd);
- }
- copy(mr_mip->w3,xd);
- if (z!=xd && z!=yd) copy(mr_mip->w1,z);
-
- MR_OUT
- return (size(mr_mip->w1));
-}
-
-int invmodp(_MIPD_ big x,big y,big z)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- int gcd;
-
- MR_IN(213);
- gcd=xgcd(_MIPP_ x,y,z,z,z);
- MR_OUT
- return gcd;
-}
-
-#else
-
-/* much smaller, much slower binary inversion algorithm */
-/* fails silently if a is not co-prime to p */
-
-/* experimental! At least 3 times slower than standard method.. */
-
-int invmodp(_MIPD_ big a,big p,big z)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- big u,v,x1,x2;
-
- MR_IN(213);
-
- u=mr_mip->w1; v=mr_mip->w2; x1=mr_mip->w3; x2=mr_mip->w4;
- copy(a,u);
- copy(p,v);
- convert(_MIPP_ 1,x1);
- zero(x2);
-
- while (size(u)!=1 && size(v)!=1)
- {
- while (remain(_MIPP_ u,2)==0)
- {
- subdiv(_MIPP_ u,2,u);
- if (remain(_MIPP_ x1,2)!=0) add(_MIPP_ x1,p,x1);
- subdiv(_MIPP_ x1,2,x1);
- }
- while (remain(_MIPP_ v,2)==0)
- {
- subdiv(_MIPP_ v,2,v);
- if (remain(_MIPP_ x2,2)!=0) add(_MIPP_ x2,p,x2);
- subdiv(_MIPP_ x2,2,x2);
- }
- if (compare(u,v)>=0)
- {
- mr_psub(_MIPP_ u,v,u);
- subtract(_MIPP_ x1,x2,x1);
- }
- else
- {
- mr_psub(_MIPP_ v,u,v);
- subtract(_MIPP_ x2,x1,x2);
- }
- }
- if (size(u)==1) copy(x1,z);
- else copy(x2,z);
-
- if (size(z)<0) add(_MIPP_ z,p,z);
-
- MR_OUT
- return 1; /* note - no checking that gcd=1 */
-}
-
-#endif
-
-#ifndef MR_STATIC
-
-/* Montgomery's method for multiple
- simultaneous modular inversions */
-
-BOOL double_inverse(_MIPD_ big n,big x,big y,big w,big z)
-{
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
-
- MR_IN(146)
-
- mad(_MIPP_ x,w,w,n,n,mr_mip->w6);
- if (size(mr_mip->w6)==0)
- {
- mr_berror(_MIPP_ MR_ERR_DIV_BY_ZERO);
- MR_OUT
- return FALSE;
- }
- invmodp(_MIPP_ mr_mip->w6,n,mr_mip->w6);
-
- mad(_MIPP_ w,mr_mip->w6,w,n,n,y);
- mad(_MIPP_ x,mr_mip->w6,x,n,n,z);
-
- MR_OUT
- return TRUE;
-}
-
-BOOL multi_inverse(_MIPD_ int m,big *x,big n,big *w)
-{ /* find w[i]=1/x[i] mod n, for i=0 to m-1 *
- * x and w MUST be distinct */
- int i;
-#ifdef MR_OS_THREADS
- miracl *mr_mip=get_mip();
-#endif
- if (m==0) return TRUE;
- if (m<0) return FALSE;
-
- MR_IN(25)
-
- if (x==w)
- {
- mr_berror(_MIPP_ MR_ERR_BAD_PARAMETERS);
- MR_OUT
- return FALSE;
- }
- if (m==1)
- {
- invmodp(_MIPP_ x[0],n,w[0]);
- MR_OUT
- return TRUE;
- }
-
- convert(_MIPP_ 1,w[0]);
- copy(x[0],w[1]);
- for (i=2;iw6); /* y=x[0]*x[1]*x[2]....x[m-1] */
- if (size(mr_mip->w6)==0)
- {
- mr_berror(_MIPP_ MR_ERR_DIV_BY_ZERO);
- MR_OUT
- return FALSE;
- }
-
- invmodp(_MIPP_ mr_mip->w6,n,mr_mip->w6);
-
-/* Now y=1/y */
-
- copy(x[m-1],mr_mip->w5);
- mad(_MIPP_ w[m-1],mr_mip->w6,mr_mip->w6,n,n,w[m-1]);
-
- for (i=m-2;;i--)
- {
- if (i==0)
- {
- mad(_MIPP_ mr_mip->w5,mr_mip->w6,mr_mip->w6,n,n,w[0]);
- break;
- }
- mad(_MIPP_ w[i],mr_mip->w5,w[i],n,n,w[i]);
- mad(_MIPP_ w[i],mr_mip->w6,w[i],n,n,w[i]);
- mad(_MIPP_ mr_mip->w5,x[i],x[i],n,n,mr_mip->w5);
- }
-
- MR_OUT
- return TRUE;
-}
-
-#endif
diff --git a/crypto/sm2/sm2_standard_enc.c b/crypto/sm2/sm2_standard_enc.c
deleted file mode 100644
index 4cfa82a6..00000000
--- a/crypto/sm2/sm2_standard_enc.c
+++ /dev/null
@@ -1,253 +0,0 @@
-/*
- * Copyright (c) 2015 - 2017 The GmSSL Project. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in
- * the documentation and/or other materials provided with the
- * distribution.
- *
- * 3. All advertising materials mentioning features or use of this
- * software must display the following acknowledgment:
- * "This product includes software developed by the GmSSL Project.
- * (http://gmssl.org/)"
- *
- * 4. The name "GmSSL Project" must not be used to endorse or promote
- * products derived from this software without prior written
- * permission. For written permission, please contact
- * guanzhi1980@gmail.com.
- *
- * 5. Products derived from this software may not be called "GmSSL"
- * nor may "GmSSL" appear in their names without prior written
- * permission of the GmSSL Project.
- *
- * 6. Redistributions of any form whatsoever must retain the following
- * acknowledgment:
- * "This product includes software developed by the GmSSL Project
- * (http://gmssl.org/)"
- *
- * THIS SOFTWARE IS PROVIDED BY THE GmSSL PROJECT ``AS IS'' AND ANY
- * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE GmSSL PROJECT OR
- * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
- * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
- * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
- * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
- * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
- * OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-
-#include
-#include
-#include
-
-
-/* test if the given array is all zero */
-int Test_Null(unsigned char array[], int len)
-{
- int i;
- i = 0;
- for (i = 0; i < len; i++)
- {
- if (array[i] != 0x00)
- return 0;
- }
- return 1;
-}
-
-
-/* sm2 encryption */
-int SM2_standard_encrypt(unsigned char* randK, epoint *pubKey, unsigned char M[], int klen, unsigned char C[])
-{
- big C1x, C1y, x2, y2, rand;
- epoint *C1, *kP, *S;
- int i;
- i = 0;
- unsigned char x2y2[SM2_NUMWORD * 2] = {0};
- SM3_STATE md;
- C1x = mirvar(0);
- C1y = mirvar(0);
- x2 = mirvar(0);
- y2 = mirvar(0);
- rand = mirvar(0);
- C1 = epoint_init();
- kP = epoint_init();
- S = epoint_init();
-
- //step2. calculate C1 = [k]G = (rGx, rGy)
- bytes_to_big(SM2_NUMWORD, randK, rand);
- ecurve_mult(rand, G, C1); //C1 = [k]G
- epoint_get(C1, C1x, C1y);
- big_to_bytes(SM2_NUMWORD, C1x, C, 1);
- big_to_bytes(SM2_NUMWORD, C1y, C + SM2_NUMWORD, 1);
-
- //step3. test if S = [h]pubKey if the point at infinity
- ecurve_mult(para_h, pubKey, S);
- if (point_at_infinity(S)) //if S is point at infinity, return error;
- return ERR_INFINITY_POINT;
-
- //step4. calculate [k]PB = (x2, y2)
- ecurve_mult(rand, pubKey, kP); //kP = [k]P
- epoint_get(kP, x2, y2);
-
- //step5. KDF(x2 || y2, klen)
- big_to_bytes(SM2_NUMWORD, x2, x2y2, 1);
- big_to_bytes(SM2_NUMWORD, y2, x2y2 + SM2_NUMWORD, 1);
- SM3_kdf(x2y2, SM2_NUMWORD * 2, klen, C + SM2_NUMWORD * 3);
- if (Test_Null(C + SM2_NUMWORD * 3, klen) != 0)
- return ERR_ARRAY_NULL;
-
- //step6. C2 = M^t
- for (i = 0; i < klen; i++)
- {
- C[SM2_NUMWORD * 3 + i] = M[i] ^ C[SM2_NUMWORD * 3 + i];
- }
-
- //step7. C3 = hash(x2, M, y2)
- SM3_init(&md);
- SM3_process(&md, x2y2, SM2_NUMWORD);
- SM3_process(&md, M, klen);
- SM3_process(&md, x2y2 + SM2_NUMWORD, SM2_NUMWORD);
- SM3_done(&md, C + SM2_NUMWORD * 2);
- return 0;
-}
-
-
-/* sm2 decryption */
-int SM2_standard_decrypt(big dB, unsigned char C[], int Clen, unsigned char M[])
-{
- SM3_STATE md;
- int i;
- i = 0;
- unsigned char x2y2[SM2_NUMWORD * 2] = {0};
- unsigned char hash[SM2_NUMWORD] = {0};
- big C1x, C1y, x2, y2;
- epoint *C1, *S, *dBC1;
- C1x = mirvar(0);
- C1y = mirvar(0);
- x2 = mirvar(0);
- y2 = mirvar(0);
- C1 = epoint_init();
- S = epoint_init();
- dBC1 = epoint_init();
-
- //step1. test if C1 fits the curve
- bytes_to_big(SM2_NUMWORD, C, C1x);
- bytes_to_big(SM2_NUMWORD, C + SM2_NUMWORD, C1y);
- epoint_set(C1x, C1y, 0, C1);
- i = Test_Point(C1);
- if (i != 0)
- return i;
-
- //step2. S = [h]C1 and test if S is the point at infinity
- ecurve_mult(para_h, C1, S);
- if (point_at_infinity(S)) // if S is point at infinity, return error;
- return ERR_INFINITY_POINT;
-
- //step3. [dB]C1 = (x2, y2)
- ecurve_mult(dB, C1, dBC1);
- epoint_get(dBC1, x2, y2);
- big_to_bytes(SM2_NUMWORD, x2, x2y2, 1);
- big_to_bytes(SM2_NUMWORD, y2, x2y2 + SM2_NUMWORD, 1);
-
- //step4. t = KDF(x2 || y2, klen)
- SM3_kdf(x2y2, SM2_NUMWORD * 2, Clen - SM2_NUMWORD * 3, M);
- if (Test_Null(M, Clen - SM2_NUMWORD * 3) != 0)
- return ERR_ARRAY_NULL;
-
- //step5. M = C2^t
- for (i = 0; i < Clen - SM2_NUMWORD * 3; i++)
- M[i] = M[i] ^ C[SM2_NUMWORD * 3 + i];
-
- //step6. hash(x2, m, y2)
- SM3_init(&md);
- SM3_process(&md, x2y2, SM2_NUMWORD);
- SM3_process(&md, M, Clen - SM2_NUMWORD * 3);
- SM3_process(&md, x2y2 + SM2_NUMWORD, SM2_NUMWORD);
- SM3_done(&md, hash);
- if (memcmp(hash, C + SM2_NUMWORD * 2, SM2_NUMWORD) != 0)
- return ERR_C3_MATCH;
- else
- return 0;
-}
-
-
-/* test whether the SM2 calculation is correct by comparing the result with the standard data */
-int SM2_standard_enc_selftest()
-{
- int tmp, i;
- tmp = 0;
- i = 0;
- unsigned char Cipher[115] = {0};
- unsigned char M[19] = {0};
- unsigned char kGxy[SM2_NUMWORD * 2] = {0};
- big ks, x, y;
- epoint *kG;
-
-
- //standard data
- unsigned char std_priKey[32] = {0x39, 0x45, 0x20, 0x8F, 0x7B, 0x21, 0x44, 0xB1, 0x3F, 0x36, 0xE3, 0x8A, 0xC6, 0xD3, 0x9F, 0x95,
- 0x88, 0x93, 0x93, 0x69, 0x28, 0x60, 0xB5, 0x1A, 0x42, 0xFB, 0x81, 0xEF, 0x4D, 0xF7, 0xC5, 0xB8};
- unsigned char std_pubKey[64] = {0x09, 0xF9, 0xDF, 0x31, 0x1E, 0x54, 0x21, 0xA1, 0x50, 0xDD, 0x7D, 0x16, 0x1E, 0x4B, 0xC5, 0xC6,
- 0x72, 0x17, 0x9F, 0xAD, 0x18, 0x33, 0xFC, 0x07, 0x6B, 0xB0, 0x8F, 0xF3, 0x56, 0xF3, 0x50, 0x20,
- 0xCC, 0xEA, 0x49, 0x0C, 0xE2, 0x67, 0x75, 0xA5, 0x2D, 0xC6, 0xEA, 0x71, 0x8C, 0xC1, 0xAA, 0x60,
- 0x0A, 0xED, 0x05, 0xFB, 0xF3, 0x5E, 0x08, 0x4A, 0x66, 0x32, 0xF6, 0x07, 0x2D, 0xA9, 0xAD, 0x13};
- unsigned char std_rand[32] = {0x59, 0x27, 0x6E, 0x27, 0xD5, 0x06, 0x86, 0x1A, 0x16, 0x68, 0x0F, 0x3A, 0xD9, 0xC0, 0x2D, 0xCC,
- 0xEF, 0x3C, 0xC1, 0xFA, 0x3C, 0xDB, 0xE4, 0xCE, 0x6D, 0x54, 0xB8, 0x0D, 0xEA, 0xC1, 0xBC, 0x21};
- unsigned char std_Message[19] = {0x65, 0x6E, 0x63, 0x72, 0x79, 0x70, 0x74, 0x69, 0x6F, 0x6E, 0x20, 0x73, 0x74, 0x61, 0x6E, 0x64,
- 0x61, 0x72, 0x64};
- unsigned char std_Cipher[115] = {0x04, 0xEB, 0xFC, 0x71, 0x8E, 0x8D, 0x17, 0x98, 0x62, 0x04, 0x32, 0x26, 0x8E, 0x77, 0xFE, 0xB6,
- 0x41, 0x5E, 0x2E, 0xDE, 0x0E, 0x07, 0x3C, 0x0F, 0x4F, 0x64, 0x0E, 0xCD, 0x2E, 0x14, 0x9A, 0x73,
- 0xE8, 0x58, 0xF9, 0xD8, 0x1E, 0x54, 0x30, 0xA5, 0x7B, 0x36, 0xDA, 0xAB, 0x8F, 0x95, 0x0A, 0x3C,
- 0x64, 0xE6, 0xEE, 0x6A, 0x63, 0x09, 0x4D, 0x99, 0x28, 0x3A, 0xFF, 0x76, 0x7E, 0x12, 0x4D, 0xF0,
- 0x59, 0x98, 0x3C, 0x18, 0xF8, 0x09, 0xE2, 0x62, 0x92, 0x3C, 0x53, 0xAE, 0xC2, 0x95, 0xD3, 0x03,
- 0x83, 0xB5, 0x4E, 0x39, 0xD6, 0x09, 0xD1, 0x60, 0xAF, 0xCB, 0x19, 0x08, 0xD0, 0xBD, 0x87, 0x66,
- 0x21, 0x88, 0x6C, 0xA9, 0x89, 0xCA, 0x9C, 0x7D, 0x58, 0x08, 0x73, 0x07, 0xCA, 0x93, 0x09, 0x2D,
- 0x65, 0x1E, 0xFA};
- mip= mirsys(1000, 16);
- mip->IOBASE = 16;
- x = mirvar(0);
- y = mirvar(0);
- ks = mirvar(0);
- kG = epoint_init();
- bytes_to_big(32, std_priKey, ks); //ks is the standard private key
-
-
- //initiate SM2 curve
- SM2_standard_init();
-
- //generate key pair
- tmp = SM2_standard_keygeneration(ks, kG);
- if (tmp != 0)
- return tmp;
- epoint_get(kG, x, y);
- big_to_bytes(SM2_NUMWORD, x, kGxy, 1);
- big_to_bytes(SM2_NUMWORD, y, kGxy + SM2_NUMWORD, 1);
- if (memcmp(kGxy, std_pubKey, SM2_NUMWORD * 2) != 0)
- return ERR_SELFTEST_KG;
-
- //encrypt data and compare the result with the standard data
- tmp = SM2_standard_encrypt(std_rand, kG, std_Message, 19, Cipher);
- if (tmp != 0)
- return tmp;
- if (memcmp(Cipher, std_Cipher, 19 + SM2_NUMWORD * 3) != 0)
- return ERR_SELFTEST_ENC;
-
- //decrypt cipher and compare the result with the standard data
- tmp = SM2_standard_decrypt(ks, Cipher, 115, M);
- if (tmp != 0)
- return tmp;
- if (memcmp(M, std_Message, 19) != 0)
- return ERR_SELFTEST_DEC;
- return 0;
-}
diff --git a/crypto/sm2/sm2_standard_exch.c b/crypto/sm2/sm2_standard_exch.c
deleted file mode 100644
index f9065df7..00000000
--- a/crypto/sm2/sm2_standard_exch.c
+++ /dev/null
@@ -1,491 +0,0 @@
-/* ====================================================================
- * Copyright (c) 2015 - 2016 The GmSSL Project. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in
- * the documentation and/or other materials provided with the
- * distribution.
- *
- * 3. All advertising materials mentioning features or use of this
- * software must display the following acknowledgment:
- * "This product includes software developed by the GmSSL Project.
- * (http://gmssl.org/)"
- *
- * 4. The name "GmSSL Project" must not be used to endorse or promote
- * products derived from this software without prior written
- * permission. For written permission, please contact
- * guanzhi1980@gmail.com.
- *
- * 5. Products derived from this software may not be called "GmSSL"
- * nor may "GmSSL" appear in their names without prior written
- * permission of the GmSSL Project.
- *
- * 6. Redistributions of any form whatsoever must retain the following
- * acknowledgment:
- * "This product includes software developed by the GmSSL Project
- * (http://gmssl.org/)"
- *
- * THIS SOFTWARE IS PROVIDED BY THE GmSSL PROJECT ``AS IS'' AND ANY
- * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE GmSSL PROJECT OR
- * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
- * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
- * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
- * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
- * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
- * OF THE POSSIBILITY OF SUCH DAMAGE.
- * ====================================================================
- *
- */
-
-
-#include
-#include
-#include
-
-
-/* calculation of w */
-int SM2_w(big n)
-{
- big n1;
- int w = 0;
- n1 = mirvar(0);
- w = logb2(para_n); //approximate integer log to the base 2 of para_n
- expb2(w, n1); //n1 = 2^w
- if (mr_compare(para_n, n1) == 1)
- w++;
- if ((w % 2) == 0)
- w = w / 2 - 1;
- else
- w = (w + 1) / 2 - 1;
- return w;
-}
-
-
-/* calculation of ZA or ZB */
-void SM3_z(unsigned char ID[], unsigned short int ELAN, epoint* pubKey, unsigned char hash[])
-{
- unsigned char Px[SM2_NUMWORD] = {0}, Py[SM2_NUMWORD] = {0};
- unsigned char IDlen[2] = {0};
- big x, y;
- SM3_STATE md;
-
- x = mirvar(0);
- y = mirvar(0);
-
- epoint_get(pubKey, x, y);
- big_to_bytes(SM2_NUMWORD, x, Px, 1);
- big_to_bytes(SM2_NUMWORD, y, Py, 1);
- memcpy(IDlen, &ELAN + 1, 1);
- memcpy(IDlen + 1, &ELAN, 1);
- SM3_init(&md);
- SM3_process(&md, IDlen, 2);
- SM3_process(&md, ID, ELAN / 8);
- SM3_process(&md, SM2_a, SM2_NUMWORD);
- SM3_process(&md, SM2_b, SM2_NUMWORD);
- SM3_process(&md, SM2_Gx, SM2_NUMWORD);
- SM3_process(&md, SM2_Gy, SM2_NUMWORD);
- SM3_process(&md, Px, SM2_NUMWORD);
- SM3_process(&md, Py, SM2_NUMWORD);
- SM3_done(&md, hash);
-
- return;
-}
-
-
-/* calculate RA */
-int SM2_standard_keyex_init_i(big ra, epoint* RA)
-{
- return SM2_standard_keygeneration(ra, RA);
-}
-
-
-/* calculate RB and a secret key */
-int SM2_standard_keyex_re_i(big rb, big dB, epoint* RA, epoint* PA, unsigned char ZA[], unsigned char ZB[], unsigned char K[], int klen, epoint* RB, epoint* V, unsigned char hash[])
-{
- SM3_STATE md;
- int i = 0, w = 0;
- unsigned char Z[SM2_NUMWORD * 2 + SM3_len / 4] = {0};
- unsigned char x1y1[SM2_NUMWORD * 2] = {0};
- unsigned char x2y2[SM2_NUMWORD * 2] = {0};
- unsigned char temp = 0x02;
- big x1, y1, x1_, x2, y2, x2_, tmp, Vx, Vy, temp_x, temp_y;
-
- //mip = mirsys(1000, 16);
- //mip->IOBASE = 16;
- x1 = mirvar(0);
- y1 = mirvar(0);
- x1_ = mirvar(0);
- x2 = mirvar(0);
- y2 = mirvar(0);
- x2_ = mirvar(0);
- tmp = mirvar(0);
- Vx = mirvar(0);
- Vy = mirvar(0);
- temp_x = mirvar(0);
- temp_y = mirvar(0);
-
- w = SM2_w(para_n);
-
- //--------B2: RB = [rb]G = (x2, y2)--------
- SM2_standard_keygeneration(rb, RB);
- epoint_get(RB, x2, y2);
- big_to_bytes(SM2_NUMWORD, x2, x2y2, 1);
- big_to_bytes(SM2_NUMWORD, y2, x2y2 + SM2_NUMWORD, 1);
-
- //--------B3: x2_ = 2^w + x2 & (2^w - 1)--------
- expb2(w, x2_); //x2_ = 2^w
- divide(x2, x2_, tmp); //x2 = x2 mod x2_ = x2 & (2^w - 1)
- add(x2_, x2, x2_);
- divide(x2_, para_n, tmp); //x2_ = n mod q
-
- //--------B4: tB = (dB + x2_ * rB) mod n--------
- multiply(x2_, rb, x2_);
- add(dB, x2_, x2_);
- divide(x2_, para_n, tmp);
-
- //--------B5: x1_ = 2^w + x1 & (2^w - 1)--------
- if (Test_Point(RA) != 0)
- return ERR_KEYEX_RA;
- epoint_get(RA, x1, y1);
- big_to_bytes(SM2_NUMWORD, x1, x1y1, 1);
- big_to_bytes(SM2_NUMWORD, y1, x1y1 + SM2_NUMWORD, 1);
- expb2(w, x1_); //x1_ = 2^w
- divide(x1, x1_, tmp); //x1 = x1 mod x1_ = x1 & (2^w - 1)
- add(x1_,x1, x1_);
- divide(x1_, para_n, tmp); //x1_ = n mod q
-
- //--------B6: V = [h * tB](PA + [x1_]RA)--------
- ecurve_mult(x1_, RA, V); //v = [x1_]RA
- epoint_get(V, temp_x, temp_y);
-
- ecurve_add(PA, V); //V = PA + V
- epoint_get(V, temp_x, temp_y);
-
- multiply(para_h, x2_, x2_); //tB = tB * h
-
- ecurve_mult(x2_, V, V);
- if (point_at_infinity(V) == 1)
- return ERR_INFINITY_POINT;
- epoint_get(V, Vx, Vy);
- big_to_bytes(SM2_NUMWORD, Vx, Z, 1);
- big_to_bytes(SM2_NUMWORD, Vy, Z + SM2_NUMWORD, 1);
-
- //------------B7:KB = KDF(VX, VY, ZA, ZB, KLEN)----------
- memcpy(Z + SM2_NUMWORD * 2, ZA, SM3_len / 8);
- memcpy(Z + SM2_NUMWORD * 2 + SM3_len / 8, ZB, SM3_len / 8);
- SM3_kdf(Z, SM2_NUMWORD * 2 + SM3_len / 4, klen / 8, K);
-
- //---------------B8:(optional)SB = hash(0x02 || Vy || HASH(Vx || ZA || ZB || x1 || y1 || x2 || y2)-------------
- SM3_init(&md);
- SM3_process(&md, Z, SM2_NUMWORD);
- SM3_process(&md, ZA, SM3_len / 8);
- SM3_process(&md, ZB, SM3_len / 8);
- SM3_process(&md, x1y1, SM2_NUMWORD * 2);
- SM3_process(&md, x2y2, SM2_NUMWORD * 2);
- SM3_done(&md, hash);
-
- SM3_init(&md);
- SM3_process(&md, &temp, 1);
- SM3_process(&md, Z + SM2_NUMWORD, SM2_NUMWORD);
- SM3_process(&md, hash, SM3_len / 8);
- SM3_done(&md, hash);
-
- return 0;
-}
-
-
-/* initiator A calculates the secret key out of RA and RB, and calculates a hash */
-int SM2_standard_keyex_init_ii(big ra, big dA, epoint* RA, epoint* RB, epoint* PB, unsigned char ZA[], unsigned char ZB[], unsigned char SB[], unsigned char K[], int klen, unsigned char SA[])
-{
- SM3_STATE md;
- int i = 0, w = 0;
- unsigned char Z[SM2_NUMWORD * 2 + SM3_len / 4] = {0};
- unsigned char x1y1[SM2_NUMWORD * 2] = {0};
- unsigned char x2y2[SM2_NUMWORD * 2] = {0};
- unsigned char hash[SM2_NUMWORD], S1[SM2_NUMWORD];
- unsigned char temp[2] = {0x02, 0x03};
- big x1, y1, x1_, x2, y2, x2_, tmp, Ux, Uy, temp_x, temp_y, tA;
- epoint* U;
- //mip = mirsys(1000, 16);
- //mip->IOBASE = 16;
-
- U = epoint_init();
- x1 = mirvar(0);
- y1 = mirvar(0);
- x1_ = mirvar(0);
- x2 = mirvar(0);
- y2 = mirvar(0);
- x2_ = mirvar(0);
- tmp = mirvar(0);
- Ux = mirvar(0);
- Uy = mirvar(0);
- temp_x = mirvar(0);
- temp_y = mirvar(0);
- tA=mirvar(0);
-
- w = SM2_w(para_n);
- epoint_get(RA, x1, y1);
- big_to_bytes(SM2_NUMWORD, x1, x1y1, TRUE);
- big_to_bytes(SM2_NUMWORD, y1, x1y1 + SM2_NUMWORD, TRUE);
-
- //--------A4: x1_ = 2^w + x2 & (2^w - 1)--------
- expb2(w, x1_); //x1_ = 2^w
- divide(x1, x1_, tmp); //x1 = x1 mod x1_ = x1 & (2^w - 1)
- add(x1_, x1, x1_);
- divide(x1_, para_n, tmp);
-
- //-------- A5:tA = (dA + x1_ * rA) mod n--------
- multiply(x1_, ra, tA);
- divide(tA, para_n, tmp);
- add(tA, dA, tA);
- divide(tA, para_n, tmp);
-
- //-------- A6:x2_ = 2^w + x2 & (2^w - 1)-----------------
- if (Test_Point(RB) != 0)
- return ERR_KEYEX_RB;//////////////////////////////////
- epoint_get(RB, x2, y2);
- big_to_bytes(SM2_NUMWORD, x2, x2y2, TRUE);
- big_to_bytes(SM2_NUMWORD, y2, x2y2 + SM2_NUMWORD, TRUE);
- expb2(w, x2_); //x2_ = 2^w
- divide(x2, x2_, tmp); //x2 = x2 mod x2_ = x2 & (2^w - 1)
- add(x2_, x2, x2_);
- divide(x2_, para_n, tmp);
-
- //--------A7:U = [h * tA](PB + [x2_]RB)-----------------
- ecurve_mult(x2_, RB, U); //U = [x2_]RB
- epoint_get(U, temp_x, temp_y);
-
- ecurve_add(PB, U); //U = PB + U
- epoint_get(U, temp_x, temp_y);
-
- multiply(para_h, tA, tA); //tA = tA * h
- divide(tA, para_n, tmp);
-
- ecurve_mult(tA, U, U);
- if (point_at_infinity(U) == 1)
- return ERR_INFINITY_POINT;
- epoint_get(U, Ux, Uy);
- big_to_bytes(SM2_NUMWORD, Ux, Z, 1);
- big_to_bytes(SM2_NUMWORD, Uy, Z + SM2_NUMWORD, 1);
-
- //------------A8:KA = KDF(UX, UY, ZA, ZB, KLEN)----------
- memcpy(Z + SM2_NUMWORD * 2, ZA, SM3_len / 8);
- memcpy(Z + SM2_NUMWORD * 2 + SM3_len / 8, ZB, SM3_len / 8);
- SM3_kdf(Z, SM2_NUMWORD * 2 + SM3_len / 4, klen / 8, K);
-
- //---------------A9:(optional) S1 = Hash(0x02 || Uy || Hash(Ux || ZA || ZB || x1 || y1 || x2 || y2))-----------
- SM3_init (&md);
- SM3_process(&md, Z, SM2_NUMWORD);
- SM3_process(&md, ZA, SM3_len / 8);
- SM3_process(&md, ZB, SM3_len / 8);
- SM3_process(&md, x1y1, SM2_NUMWORD * 2);
- SM3_process(&md, x2y2, SM2_NUMWORD * 2);
- SM3_done(&md, hash);
-
- SM3_init(&md);
- SM3_process(&md, temp, 1);
- SM3_process(&md, Z + SM2_NUMWORD, SM2_NUMWORD);
- SM3_process(&md, hash, SM3_len / 8);
- SM3_done(&md, S1);
-
- //test S1 = SB?
- if (memcmp(S1, SB, SM2_NUMWORD) != 0)
- return ERR_EQUAL_S1SB;
-
- //---------------A10 SA = Hash(0x03 || yU || Hash(xU || ZA || ZB || x1 || y1 || x2 || y2))-------------
- SM3_init(&md);
- SM3_process(&md, &temp[1], 1);
- SM3_process(&md, Z + SM2_NUMWORD, SM2_NUMWORD);
- SM3_process(&md, hash, SM3_len / 8);
- SM3_done(&md, SA);
-
- return 0;
-}
-
-
-/* (optional)Step B10: verifies the hash value received from initiator A */
-int SM2_standard_keyex_re_ii(epoint *V, epoint *RA, epoint *RB, unsigned char ZA[], unsigned char ZB[], unsigned char SA[])
-{
- big x1, y1, x2, y2, Vx, Vy;
- unsigned char hash[SM2_NUMWORD], S2[SM2_NUMWORD];
- unsigned char temp = 0x03;
- unsigned char xV[SM2_NUMWORD], yV[SM2_NUMWORD];
- unsigned char x1y1[SM2_NUMWORD * 2] = {0};
- unsigned char x2y2[SM2_NUMWORD * 2] = {0};
- SM3_STATE md;
-
- x1 = mirvar(0);
- y1 = mirvar(0);
- x2 = mirvar(0);
- y2 = mirvar(0);
- Vx = mirvar(0);
- Vy = mirvar(0);
-
- epoint_get(RA, x1, y1);
- epoint_get(RB, x2, y2);
- epoint_get(V, Vx, Vy);
-
- big_to_bytes(SM2_NUMWORD, Vx, xV, TRUE);
- big_to_bytes(SM2_NUMWORD, Vy, yV, TRUE);
- big_to_bytes(SM2_NUMWORD, x1, x1y1, TRUE);
- big_to_bytes(SM2_NUMWORD, y1, x1y1 + SM2_NUMWORD, TRUE);
- big_to_bytes(SM2_NUMWORD, x2, x2y2, TRUE);
- big_to_bytes(SM2_NUMWORD, y2, x2y2 + SM2_NUMWORD, TRUE);
-
- //---------------B10:(optional) S2 = Hash(0x03 || Vy || Hash(Vx || ZA || ZB || x1 || y1 || x2 || y2))
- SM3_init(&md);
- SM3_process(&md, xV, SM2_NUMWORD);
- SM3_process(&md, ZA, SM3_len / 8);
- SM3_process(&md, ZB, SM3_len / 8);
- SM3_process(&md, x1y1, SM2_NUMWORD * 2);
- SM3_process(&md, x2y2, SM2_NUMWORD * 2);
- SM3_done(&md, hash);
-
- SM3_init(&md);
- SM3_process(&md, &temp, 1);
- SM3_process(&md, yV, SM2_NUMWORD);
- SM3_process(&md, hash, SM3_len / 8);
- SM3_done(&md, S2);
-
- if (memcmp(S2, SA, SM3_len / 8) != 0)
- return ERR_EQUAL_S2SA;
-
- return 0;
-}
-
-
-/* self check of SM2 key exchange */
-int SM2_standard_keyex_selftest()
-{
- //standard data
- unsigned char std_priKeyA[SM2_NUMWORD] = {0x81, 0xEB, 0x26, 0xE9, 0x41, 0xBB, 0x5A, 0xF1, 0x6D, 0xF1, 0x16, 0x49, 0x5F, 0x90, 0x69, 0x52,
- 0x72, 0xAE, 0x2C, 0xD6, 0x3D, 0x6C, 0x4A, 0xE1, 0x67, 0x84, 0x18, 0xBE, 0x48, 0x23, 0x00, 0x29};
- unsigned char std_pubKeyA[SM2_NUMWORD * 2] = {0x16, 0x0E, 0x12, 0x89, 0x7D, 0xF4, 0xED, 0xB6, 0x1D, 0xD8, 0x12, 0xFE, 0xB9, 0x67, 0x48,
- 0xFB, 0xD3, 0xCC, 0xF4, 0xFF, 0xE2, 0x6A, 0xA6, 0xF6, 0xDB, 0x95, 0x40, 0xAF, 0x49, 0xC9,
- 0x42, 0x32, 0x4A, 0x7D, 0xAD, 0x08, 0xBB, 0x9A, 0x45, 0x95, 0x31, 0x69, 0x4B, 0xEB, 0x20,
- 0xAA, 0x48, 0x9D, 0x66, 0x49, 0x97, 0x5E, 0x1B, 0xFC, 0xF8, 0xC4, 0x74, 0x1B, 0x78, 0xB4,
- 0xB2, 0x23, 0x00, 0x7F};
- unsigned char std_randA[SM2_NUMWORD] = {0xD4, 0xDE, 0x15, 0x47, 0x4D, 0xB7, 0x4D, 0x06, 0x49, 0x1C, 0x44, 0x0D, 0x30, 0x5E, 0x01, 0x24,
- 0x00, 0x99, 0x0F, 0x3E, 0x39, 0x0C, 0x7E, 0x87, 0x15, 0x3C, 0x12, 0xDB, 0x2E, 0xA6, 0x0B, 0xB3};
- unsigned char std_priKeyB[SM2_NUMWORD] = {0x78, 0x51, 0x29, 0x91, 0x7D, 0x45, 0xA9, 0xEA, 0x54, 0x37, 0xA5, 0x93, 0x56, 0xB8, 0x23, 0x38,
- 0xEA, 0xAD, 0xDA, 0x6C, 0xEB, 0x19, 0x90, 0x88, 0xF1, 0x4A, 0xE1, 0x0D, 0xEF, 0xA2, 0x29, 0xB5};
- unsigned char std_pubKeyB[SM2_NUMWORD * 2] = {0x6A, 0xE8, 0x48, 0xC5, 0x7C, 0x53, 0xC7, 0xB1, 0xB5, 0xFA, 0x99, 0xEB, 0x22, 0x86, 0xAF,
- 0x07, 0x8B, 0xA6, 0x4C, 0x64, 0x59, 0x1B, 0x8B, 0x56, 0x6F, 0x73, 0x57, 0xD5, 0x76, 0xF1,
- 0x6D, 0xFB, 0xEE, 0x48, 0x9D, 0x77, 0x16, 0x21, 0xA2, 0x7B, 0x36, 0xC5, 0xC7, 0x99, 0x20,
- 0x62, 0xE9, 0xCD, 0x09, 0xA9, 0x26, 0x43, 0x86, 0xF3, 0xFB, 0xEA, 0x54, 0xDF, 0xF6, 0x93,
- 0x05, 0x62, 0x1C, 0x4D};
- unsigned char std_randB[SM2_NUMWORD] = {0x7E, 0x07, 0x12, 0x48, 0x14, 0xB3, 0x09, 0x48, 0x91, 0x25, 0xEA, 0xED, 0x10, 0x11, 0x13, 0x16,
- 0x4E, 0xBF, 0x0F, 0x34, 0x58, 0xC5, 0xBD, 0x88, 0x33, 0x5C, 0x1F, 0x9D, 0x59, 0x62, 0x43, 0xD6};
- unsigned char std_IDA[16] = {0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38};
- unsigned char std_IDB[16] = {0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38};
- unsigned short int std_ENTLA = 0x0080;
- unsigned short int std_ENTLB = 0x0080;
- unsigned char std_ZA[SM3_len] = {0x3B, 0x85, 0xA5, 0x71, 0x79, 0xE1, 0x1E, 0x7E, 0x51, 0x3A, 0xA6, 0x22, 0x99, 0x1F, 0x2C,
- 0xA7, 0x4D, 0x18, 0x07, 0xA0, 0xBD, 0x4D, 0x4B, 0x38, 0xF9, 0x09, 0x87, 0xA1, 0x7A, 0xC2,
- 0x45, 0xB1};
- unsigned char std_ZB[SM3_len] = {0x79, 0xC9, 0x88, 0xD6, 0x32, 0x29, 0xD9, 0x7E, 0xF1, 0x9F, 0xE0, 0x2C, 0xA1, 0x05, 0x6E,
- 0x01, 0xE6, 0xA7, 0x41, 0x1E, 0xD2, 0x46, 0x94, 0xAA, 0x8F, 0x83, 0x4F, 0x4A, 0x4A, 0xB0,
- 0x22, 0xF7};
- unsigned char std_RA[SM2_NUMWORD * 2] = {0x64, 0xCE, 0xD1, 0xBD, 0xBC, 0x99, 0xD5, 0x90, 0x04, 0x9B, 0x43, 0x4D, 0x0F, 0xD7, 0x34, 0x28,
- 0xCF, 0x60, 0x8A, 0x5D, 0xB8, 0xFE, 0x5C, 0xE0, 0x7F, 0x15, 0x02, 0x69, 0x40, 0xBA, 0xE4, 0x0E,
- 0x37, 0x66, 0x29, 0xC7, 0xAB, 0x21, 0xE7, 0xDB, 0x26, 0x09, 0x22, 0x49, 0x9D, 0xDB, 0x11, 0x8F,
- 0x07, 0xCE, 0x8E, 0xAA, 0xE3, 0xE7, 0x72, 0x0A, 0xFE, 0xF6, 0xA5, 0xCC, 0x06, 0x20, 0x70, 0xC0};
- unsigned char std_K[16] = {0x6C, 0x89, 0x34, 0x73, 0x54, 0xDE, 0x24, 0x84, 0xC6, 0x0B, 0x4A, 0xB1, 0xFD, 0xE4, 0xC6, 0xE5};
- unsigned char std_RB[SM2_NUMWORD * 2] = {0xAC, 0xC2, 0x76, 0x88, 0xA6, 0xF7, 0xB7, 0x06, 0x09, 0x8B, 0xC9, 0x1F, 0xF3, 0xAD, 0x1B, 0xFF,
- 0x7D, 0xC2, 0x80, 0x2C, 0xDB, 0x14, 0xCC, 0xCC, 0xDB, 0x0A, 0x90, 0x47, 0x1F, 0x9B, 0xD7, 0x07,
- 0x2F, 0xED, 0xAC, 0x04, 0x94, 0xB2, 0xFF, 0xC4, 0xD6, 0x85, 0x38, 0x76, 0xC7, 0x9B, 0x8F, 0x30,
- 0x1C, 0x65, 0x73, 0xAD, 0x0A, 0xA5, 0x0F, 0x39, 0xFC, 0x87, 0x18, 0x1E, 0x1A, 0x1B, 0x46, 0xFE};
- unsigned char std_SB[SM3_len] = {0xD3, 0xA0, 0xFE, 0x15, 0xDE, 0xE1, 0x85, 0xCE, 0xAE, 0x90, 0x7A, 0x6B, 0x59, 0x5C, 0xC3,
- 0x2A, 0x26, 0x6E, 0xD7, 0xB3, 0x36, 0x7E, 0x99, 0x83, 0xA8, 0x96, 0xDC, 0x32, 0xFA, 0x20,
- 0xF8, 0xEB};
- int std_Klen = 128; //bit len
- int temp;
-
- big x, y, dA, dB, rA, rB;
- epoint* pubKeyA, *pubKeyB, *RA, *RB, *V;
-
- unsigned char hash[SM3_len / 8] = {0};
- unsigned char ZA[SM3_len / 8] = {0};
- unsigned char ZB[SM3_len / 8] = {0};
- unsigned char xy[SM2_NUMWORD * 2] = {0};
- unsigned char *KA, *KB;
- unsigned char SA[SM3_len / 8];
-
- KA = malloc(std_Klen / 8);
- KB = malloc(std_Klen / 8);
-
- mip = mirsys(1000, 16);
- mip->IOBASE = 16;
-
- x = mirvar(0);
- y = mirvar(0);
- dA = mirvar(0);
- dB = mirvar(0);
- rA = mirvar(0);
- rB = mirvar(0);
- pubKeyA = epoint_init();
- pubKeyB = epoint_init();
- RA = epoint_init();
- RB = epoint_init();
- V = epoint_init();
-
- SM2_standard_init();
-
- bytes_to_big(SM2_NUMWORD, std_priKeyA, dA);
- bytes_to_big(SM2_NUMWORD, std_priKeyB, dB);
- bytes_to_big(SM2_NUMWORD, std_randA, rA);
- bytes_to_big(SM2_NUMWORD, std_randB, rB);
- bytes_to_big(SM2_NUMWORD, std_pubKeyA, x);
- bytes_to_big(SM2_NUMWORD, std_pubKeyA + SM2_NUMWORD, y);
- epoint_set(x, y, 0, pubKeyA);
- bytes_to_big(SM2_NUMWORD, std_pubKeyB, x);
- bytes_to_big(SM2_NUMWORD, std_pubKeyB + SM2_NUMWORD, y);
- epoint_set(x, y, 0, pubKeyB);
-
- SM3_z(std_IDA, std_ENTLA, pubKeyA, ZA);
- if (memcmp(ZA, std_ZA, SM3_len / 8) != 0)
- return ERR_SELFTEST_Z;
- SM3_z(std_IDB, std_ENTLB, pubKeyB, ZB);
- if (memcmp(ZB, std_ZB, SM3_len / 8) != 0)
- return ERR_SELFTEST_Z;
-
- temp = SM2_standard_keyex_init_i(rA, RA);
- if (temp)
- return temp;
-
- epoint_get(RA, x, y);
- big_to_bytes(SM2_NUMWORD, x, xy, 1);
- big_to_bytes(SM2_NUMWORD, y, xy + SM2_NUMWORD, 1);
- if (memcmp(xy, std_RA, SM2_NUMWORD * 2) != 0)
- return ERR_SELFTEST_INI_I;
-
- temp = SM2_standard_keyex_re_i(rB, dB, RA, pubKeyA, ZA, ZB, KA, std_Klen, RB, V, hash);
- if (temp)
- return temp;
- if (memcmp(KA, std_K, std_Klen / 8) != 0)
- return ERR_SELFTEST_RES_I;
-
- temp = SM2_standard_keyex_init_ii(rA, dA, RA, RB, pubKeyB, ZA, ZB, hash, KB, std_Klen, SA);
- if (temp)
- return temp;
- if (memcmp(KB, std_K, std_Klen / 8) != 0)
- return ERR_SELFTEST_INI_II;
-
- if (SM2_standard_keyex_re_ii(V, RA, RB, ZA, ZB, SA) != 0)
- return ERR_EQUAL_S2SA;
-
- free(KA);
- free(KB);
- return 0;
-}
diff --git a/crypto/sm2/sm2_standard_sign.c b/crypto/sm2/sm2_standard_sign.c
deleted file mode 100644
index 4b447613..00000000
--- a/crypto/sm2/sm2_standard_sign.c
+++ /dev/null
@@ -1,349 +0,0 @@
-/* ====================================================================
- * Copyright (c) 2015 - 2016 The GmSSL Project. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in
- * the documentation and/or other materials provided with the
- * distribution.
- *
- * 3. All advertising materials mentioning features or use of this
- * software must display the following acknowledgment:
- * "This product includes software developed by the GmSSL Project.
- * (http://gmssl.org/)"
- *
- * 4. The name "GmSSL Project" must not be used to endorse or promote
- * products derived from this software without prior written
- * permission. For written permission, please contact
- * guanzhi1980@gmail.com.
- *
- * 5. Products derived from this software may not be called "GmSSL"
- * nor may "GmSSL" appear in their names without prior written
- * permission of the GmSSL Project.
- *
- * 6. Redistributions of any form whatsoever must retain the following
- * acknowledgment:
- * "This product includes software developed by the GmSSL Project
- * (http://gmssl.org/)"
- *
- * THIS SOFTWARE IS PROVIDED BY THE GmSSL PROJECT ``AS IS'' AND ANY
- * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE GmSSL PROJECT OR
- * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
- * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
- * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
- * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
- * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
- * OF THE POSSIBILITY OF SUCH DAMAGE.
- * ====================================================================
- */
-
-
-#include
-#include
-#include
-
-
-
-/* test if the big x is zero */
-int Test_Zero(big x)
-{
- big zero;
- zero = mirvar(0);
- if (mr_compare(x, zero) == 0)
- return 1;
- else
- return 0;
-}
-
-
-/* test if the big x is order n */
-int Test_n(big x)
-{
- //bytes_to_big(32, SM2_n, n);
- if (mr_compare(x, para_n) == 0)
- return 1;
- else
- return 0;
-}
-
-
-/* test if the big x belong to the range[1, n-1] */
-int Test_Range(big x)
-{
- big one, decr_n;
-
- one = mirvar(0);
- decr_n = mirvar(0);
-
- convert(1, one);
- decr(para_n, 1, decr_n);
-
- if ((mr_compare(x, one) < 0) | (mr_compare(x, decr_n) > 0))
- return 1;
- return 0;
-}
-
-
-/* calculate a pubKey out of a given priKey */
-int SM2_standard_sign_keygeneration(unsigned char PriKey[], unsigned char Px[], unsigned char Py[])
-{
- int i = 0;
- big d, PAx, PAy;
- epoint *PA;
-
- SM2_standard_init();
- PA = epoint_init();
-
- d = mirvar(0);
- PAx = mirvar(0);
- PAy = mirvar(0);
-
- bytes_to_big(SM2_NUMWORD, PriKey, d);
-
- ecurve_mult(d, G, PA);
- epoint_get(PA, PAx, PAy);
-
- big_to_bytes(SM2_NUMWORD, PAx, Px, TRUE);
- big_to_bytes(SM2_NUMWORD, PAy, Py, TRUE);
- i = Test_PubKey(PA);
- if (i)
- return i;
- else
- return 0;
-}
-
-
-/* SM2 signature algorithm */
-int SM2_standard_sign(unsigned char *message, int len, unsigned char ZA[], unsigned char rand[], unsigned char d[], unsigned char R[], unsigned char S[])
-{
- unsigned char hash[SM3_len / 8];
- int M_len = len + SM3_len / 8;
- unsigned char *M = NULL;
- int i;
-
- big dA, r, s, e, k, KGx, KGy;
- big rem, rk, z1, z2;
- epoint *KG;
-
- i = SM2_standard_init();
- if (i)
- return i;
- //initiate
- dA = mirvar(0);
- e = mirvar(0);
- k = mirvar(0);
- KGx = mirvar(0);
- KGy = mirvar(0);
- r = mirvar(0);
- s = mirvar(0);
- rem = mirvar(0);
- rk = mirvar(0);
- z1 = mirvar(0);
- z2 = mirvar(0);
-
- bytes_to_big(SM2_NUMWORD, d, dA); //cinstr(dA, d);
-
- KG = epoint_init();
-
- //step1, set M = ZA || M
- M = (char *)malloc(sizeof(char)*(M_len + 1));
- memcpy(M, ZA, SM3_len / 8);
- memcpy(M + SM3_len / 8, message, len);
-
- //step2, generate e = H(M)
- SM3_256(M, M_len, hash);
- bytes_to_big(SM3_len / 8, hash, e);
-
- //step3:generate k
- bytes_to_big(SM3_len / 8, rand, k);
-
- //step4:calculate kG
- ecurve_mult(k, G, KG);
-
- //step5:calculate r
- epoint_get(KG, KGx, KGy);
- add(e, KGx, r);
- divide(r, para_n, rem);
-
- //judge r = 0 or n + k = n?
- add(r, k, rk);
- if (Test_Zero(r) | Test_n(rk))
- return ERR_GENERATE_R;
-
- //step6:generate s
- incr(dA, 1, z1);
- xgcd(z1, para_n, z1, z1, z1);
- multiply(r, dA, z2);
- divide(z2, para_n, rem);
- subtract(k, z2, z2);
- add(z2, para_n, z2);
- multiply(z1, z2, s);
- divide(s, para_n, rem);
-
- //judge s = 0?
- if (Test_Zero(s))
- return ERR_GENERATE_S ;
-
- big_to_bytes(SM2_NUMWORD, r, R, TRUE);
- big_to_bytes(SM2_NUMWORD, s, S, TRUE);
-
- free(M);
- return 0;
-}
-
-
-/* SM2 verification algorithm */
-int SM2_standard_verify(unsigned char *message, int len, unsigned char ZA[], unsigned char Px[], unsigned char Py[], unsigned char R[], unsigned char S[])
-{
- unsigned char hash[SM3_len / 8];
- int M_len = len + SM3_len / 8;
- unsigned char *M = NULL;
- int i;
-
- big PAx, PAy, r, s, e, t, rem, x1, y1;
- big RR;
- epoint *PA, *sG, *tPA;
-
- i = SM2_standard_init();
- if (i)
- return i;
-
- PAx = mirvar(0);
- PAy = mirvar(0);
- r = mirvar(0);
- s = mirvar(0);
- e = mirvar(0);
- t = mirvar(0);
- x1 = mirvar(0);
- y1 = mirvar(0);
- rem = mirvar(0);
- RR = mirvar(0);
-
- PA = epoint_init();
- sG = epoint_init();
- tPA = epoint_init();
-
- bytes_to_big(SM2_NUMWORD, Px, PAx);
- bytes_to_big(SM2_NUMWORD, Py, PAy);
-
- bytes_to_big(SM2_NUMWORD, R, r);
- bytes_to_big(SM2_NUMWORD, S, s);
-
- if (!epoint_set(PAx, PAy, 0, PA)) //initialise public key
- {
- return ERR_PUBKEY_INIT;
- }
-
- //step1: test if r belong to [1, n-1]
- if (Test_Range(r))
- return ERR_OUTRANGE_R;
-
- //step2: test if s belong to [1, n-1]
- if (Test_Range(s))
- return ERR_OUTRANGE_S;
-
- //step3, generate M
- M = (char *)malloc(sizeof(char)*(M_len + 1));
- memcpy(M, ZA, SM3_len / 8);
- memcpy(M + SM3_len / 8, message, len);
-
- //step4, generate e = H(M)
- SM3_256(M, M_len, hash);
- bytes_to_big(SM3_len / 8, hash, e);
-
- //step5:generate t
- add(r, s, t);
- divide(t, para_n, rem);
-
- if (Test_Zero(t))
- return ERR_GENERATE_T;
-
- //step 6: generate(x1, y1)
- ecurve_mult(s, G, sG);
- ecurve_mult(t, PA, tPA);
- ecurve_add(sG, tPA);
- epoint_get(tPA, x1, y1);
-
- //step7:generate RR
- add(e, x1, RR);
- divide(RR, para_n, rem);
-
- free(M);
- if (mr_compare(RR, r) == 0)
- return 0;
- else
- return ERR_DATA_MEMCMP;
-}
-
-
-/* SM2 self check */
-int SM2_standard_selfcheck()
-{
- //the private key
- unsigned char dA[32] = {0x39, 0x45, 0x20, 0x8f, 0x7b, 0x21, 0x44, 0xb1, 0x3f, 0x36, 0xe3, 0x8a, 0xc6, 0xd3, 0x9f,
- 0x95, 0x88, 0x93, 0x93, 0x69, 0x28, 0x60, 0xb5, 0x1a, 0x42, 0xfb, 0x81, 0xef, 0x4d, 0xf7,
- 0xc5, 0xb8};
- unsigned char rand[32] = {0x59, 0x27, 0x6E, 0x27, 0xD5, 0x06, 0x86, 0x1A, 0x16, 0x68, 0x0F, 0x3A, 0xD9, 0xC0, 0x2D,
- 0xCC, 0xEF, 0x3C, 0xC1, 0xFA, 0x3C, 0xDB, 0xE4, 0xCE, 0x6D, 0x54, 0xB8, 0x0D, 0xEA, 0xC1,
- 0xBC, 0x21};
- //the public key
- /* unsigned char xA[32] = {0x09, 0xf9, 0xdf, 0x31, 0x1e, 0x54, 0x21, 0xa1, 0x50, 0xdd, 0x7d, 0x16, 0x1e, 0x4b, 0xc5,
- 0xc6, 0x72, 0x17, 0x9f, 0xad, 0x18, 0x33, 0xfc, 0x07, 0x6b, 0xb0, 0x8f, 0xf3, 0x56, 0xf3,
- 0x50, 0x20};
- unsigned char yA[32] = {0xcc, 0xea, 0x49, 0x0c, 0xe2, 0x67, 0x75, 0xa5, 0x2d, 0xc6, 0xea, 0x71, 0x8c, 0xc1, 0xaa,
- 0x60, 0x0a, 0xed, 0x05, 0xfb, 0xf3, 0x5e, 0x08, 0x4a, 0x66, 0x32, 0xf6, 0x07, 0x2d, 0xa9,
- 0xad, 0x13};*/
-
- unsigned char xA[32], yA[32];
- unsigned char r[32], s[32]; // Signature
-
- unsigned char IDA[16] = {0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x31, 0x32, 0x33,
- 0x34, 0x35, 0x36, 0x37, 0x38}; //ASCII code of userA's identification
- int IDA_len = 16;
- unsigned char ENTLA[2] = {0x00, 0x80}; //the length of userA's identification, presentation in ASCII code
-
- unsigned char *message = "message digest"; //the message to be signed
- int len = strlen(message); //the length of message
- unsigned char ZA[SM3_len / 8]; //ZA = Hash(ENTLA || IDA || a || b || Gx || Gy || xA|| yA)
- unsigned char Msg[210]; //210 = IDA_len + 2 + SM2_NUMWORD * 6
-
- int temp;
-
- mip = mirsys(10000, 16);
- mip->IOBASE = 16;
-
- temp = SM2_standard_sign_keygeneration(dA, xA, yA);
- if (temp)
- return temp;
-
- //ENTLA || IDA || a || b || Gx || Gy || xA || yA
- memcpy(Msg, ENTLA, 2);
- memcpy(Msg + 2, IDA, IDA_len);
- memcpy(Msg + 2 + IDA_len, SM2_a, SM2_NUMWORD);
- memcpy(Msg + 2 + IDA_len + SM2_NUMWORD, SM2_b, SM2_NUMWORD);
- memcpy(Msg + 2 + IDA_len + SM2_NUMWORD * 2, SM2_Gx, SM2_NUMWORD);
- memcpy(Msg + 2 + IDA_len + SM2_NUMWORD * 3, SM2_Gy, SM2_NUMWORD);
- memcpy(Msg + 2 + IDA_len + SM2_NUMWORD * 4, xA, SM2_NUMWORD);
- memcpy(Msg + 2 + IDA_len + SM2_NUMWORD * 5, yA, SM2_NUMWORD);
- SM3_256(Msg, 210, ZA);
-
- temp = SM2_standard_sign(message, len, ZA, rand, dA, r, s);
- if (temp)
- return temp;
-
- temp = SM2_standard_verify(message, len, ZA, xA, yA, r, s);
- if (temp)
- return temp;
-
- return 0;
-}