⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 p1363.c

📁 miracl-大数运算库,大家使用有什么问题请多多提意见
💻 C
📖 第 1 页 / 共 5 页
字号:

P1363_API BOOL AES_CBC_IV0_ENCRYPT(octet *k,octet *m,FILE *ifp,octet *c,FILE *ofp)
{ /* AES CBC encryption, with Null IV */
  /* Input is from either an octet string m, or from a file plain, 
     output is to an octet string c, or a file cipher */
    aes a;
    int i,j,ipt,opt,ch;
    char buff[16];
    BOOL fin;
    int padlen;
    if (m!=NULL && ifp!=NULL) return FALSE;
    if (c!=NULL)
    {
        if (ofp!=NULL) return FALSE;
        OCTET_CLEAR(c);
    }
    if (!aes_init(&a,MR_CBC,k->len,k->val,NULL)) return FALSE;

    ipt=opt=0;
    fin=FALSE;
    forever
    {
        for (i=0;i<16;i++)
        {
            if (m!=NULL) 
            {
                if (ipt<m->len) buff[i]=m->val[ipt++];
                else {fin=TRUE; break;}
            }
            if (ifp!=NULL) 
            { 
                if ((ch=fgetc(ifp))!=EOF) buff[i]=ch;
                else {fin=TRUE; break;}
            }
        }
        if (fin) break;
        aes_encrypt(&a,buff);
        for (i=0;i<16;i++)
        {
            if (c!=NULL) if (opt<c->max) c->val[opt++]=buff[i];
            if (ofp!=NULL) fputc(buff[i],ofp); 
        }   
    }    

/* last block, filled up to i-th index */

    padlen=16-i;
    for (j=i;j<16;j++) buff[j]=padlen;
    aes_encrypt(&a,buff);
    for (i=0;i<16;i++)
    {
        if (c!=NULL) if (opt<c->max) c->val[opt++]=buff[i];
        if (ofp!=NULL) fputc(buff[i],ofp);
    }   
    aes_end(&a);
    if (c!=NULL) c->len=opt;    
    return TRUE;
}

/*** DL primitives - support functions ***/
/* Destroy the DL Domain structure */

P1363_API void DL_DOMAIN_KILL(dl_domain *DOM)
{
    OCTET_KILL(&DOM->Q);
    OCTET_KILL(&DOM->R);
    OCTET_KILL(&DOM->G);
    OCTET_KILL(&DOM->K);
    OCTET_KILL(&DOM->IK);

    if (DOM->PC.store!=0) 
        brick_end(&DOM->PC);        
    DOM->words=DOM->fsize=0; DOM->H=DOM->rbits=0;
}

/* Initialise the DL domain structure
 * It is assumed that the DL domain details are obtained from a file
 * or from an array of strings 
 * multi-precision numbers are read in in Hex
 * A suitable file can be generated offline by the MIRACL example program
 * dssetup.c   
 * Set precompute=TRUE if a precomputed table is to be used to 
 * speed up the calculation g^x mod p 
 * Returns recommended number of bytes for use with octet strings */

P1363_API int DL_DOMAIN_INIT(dl_domain *DOM,char *fname,char **params,BOOL precompute)
{ /* get domain details from specified file, OR from an array of strings   *
   * If input from a file, params=NULL, if input from strings, fname=NULL  *
   * returns filed size in bytes                                           */ 
    FILE *fp;
    BOOL fileinput=TRUE;
    miracl *mr_mip;
    big q,r,g,k;
    int bits,rbits,bytes,rbytes,err,res=0;

#ifndef MR_STATIC
    char *mem;
#else
    char mem[MR_BIG_RESERVE(4)];
    memset(mem,0,MR_BIG_RESERVE(4));
#endif
    
    if (fname==NULL && params==NULL) return MR_P1363_DOMAIN_NOT_FOUND;
    if (fname==NULL) fileinput=FALSE;

    if (fileinput)
    {
        fp=fopen(fname,"rt");
        if (fp==NULL) return MR_P1363_DOMAIN_NOT_FOUND;
        fscanf(fp,"%d\n",&bits);
    }
    else
        sscanf(params[0],"%d\n",&bits); 

    DOM->words=MR_ROUNDUP(bits,MIRACL);
        
    mr_mip=mirsys(MR_ROUNDUP(bits,4),16);
    if (mr_mip==NULL) 
    {
        if (fileinput) fclose(fp);
        return MR_P1363_OUT_OF_MEMORY;
    }
#ifndef MR_STATIC
    mem=memalloc(_MIPP_ 4);
    if (mem==NULL)
    {
        if (fileinput) fclose(fp);
        res=MR_P1363_OUT_OF_MEMORY;
    }
#endif

    mr_mip->ERCON=TRUE;

    if (res==0)
    {
        q=mirvar_mem(_MIPP_ mem,0);
        r=mirvar_mem(_MIPP_ mem,1);
        g=mirvar_mem(_MIPP_ mem,2);
        k=mirvar_mem(_MIPP_ mem,3);

        bytes=MR_ROUNDUP(bits,8);

        if (fileinput)
        {
            innum(_MIPP_ q,fp);
            innum(_MIPP_ r,fp);
            innum(_MIPP_ g,fp);
            
            fclose(fp);
        }
        else
        {
            instr(_MIPP_ q,params[1]);
            instr(_MIPP_ r,params[2]);
            instr(_MIPP_ g,params[3]);
        } 
         
        rbits=logb2(_MIPP_ r);       /* r is usually much smaller than q */
        rbytes=MR_ROUNDUP(rbits,8);
        
        OCTET_INIT(&DOM->Q,bytes);
        OCTET_INIT(&DOM->R,rbytes);
        OCTET_INIT(&DOM->G,bytes);
        OCTET_INIT(&DOM->K,bytes);
        OCTET_INIT(&DOM->IK,rbytes);
        DOM->H=(1+rbits)/2;
        DOM->fsize=bytes;
        DOM->rbits=rbits;
        decr(_MIPP_ q,1,k);
        divide(_MIPP_ k,r,k);    /* k=(q-1)/r */
    
        convert_big_octet(_MIPP_ q,&DOM->Q);
        convert_big_octet(_MIPP_ r,&DOM->R);
        convert_big_octet(_MIPP_ g,&DOM->G);
        convert_big_octet(_MIPP_ k,&DOM->K);
        xgcd(_MIPP_ k,r,k,k,k);
        convert_big_octet(_MIPP_ k,&DOM->IK);
        DOM->PC.store=0;
        if (precompute) brick_init(_MIPP_ &DOM->PC,g,q,logb2(_MIPP_ r));
    }
#ifndef MR_STATIC
    memkill(_MIPP_ mem,4);
#else
    memset(mem,0,MR_BIG_RESERVE(4));
#endif
    err=mr_mip->ERNUM;
    mirexit(_MIPPO_ );

    if (err==MR_ERR_OUT_OF_MEMORY) return MR_P1363_OUT_OF_MEMORY;
    if (err==MR_ERR_DIV_BY_ZERO) return MR_P1363_DIV_BY_ZERO;
    if (err!=0) return -(1000+err);
    if (res<0) return res;
    else return bytes;
}

/* validate DL domain details - good idea if you got them from
 * some-one else! */

P1363_API int DL_DOMAIN_VALIDATE(BOOL (*idle)(void),dl_domain *DOM)
{ /* do domain checks - IEEE P1363 A16.2 */
    miracl *mr_mip=mirsys(DOM->words,0);
    big q,r,g,t;
    int err,res=0;
#ifndef MR_STATIC
    char *mem;
#else
    char mem[MR_BIG_RESERVE(4)];
    memset(mem,0,MR_BIG_RESERVE(4));
#endif

    if (mr_mip==NULL) return MR_P1363_OUT_OF_MEMORY;

    mr_mip->ERCON=TRUE;
    mr_mip->NTRY=50;
    set_user_function(_MIPP_ idle);
#ifndef MR_STATIC
    mem=memalloc(_MIPP_ 4);
    if (mem==NULL) res=MR_P1363_OUT_OF_MEMORY;
#endif
    if (res==0)
    {
        q=mirvar_mem(_MIPP_ mem,0);
        r=mirvar_mem(_MIPP_ mem,1);
        g=mirvar_mem(_MIPP_ mem,2);
        t=mirvar_mem(_MIPP_ mem,3);

        OS2FEP(_MIPP_ &DOM->Q,q);
        OS2FEP(_MIPP_ &DOM->R,r);
        OS2FEP(_MIPP_ &DOM->G,g);
        if (size(g)<2 || size(q)<=2 || size(r)<=2) res=MR_P1363_DOMAIN_ERROR; 
        if (compare(g,q)>=0) res=MR_P1363_DOMAIN_ERROR;
    }
    if (res==0)
    {
        gprime(_MIPP_ 10000);
        if (!isprime(_MIPP_ q)) res=MR_P1363_DOMAIN_ERROR;
    }
    if (res==0) 
    {
        if (!isprime(_MIPP_ r)) res=MR_P1363_DOMAIN_ERROR;
    }
    if (res==0)
    { /* is g of order r? */
       powmod(_MIPP_ g,r,q,t);
       if (size(t)!=1) res=MR_P1363_DOMAIN_ERROR;
    }
#ifndef MR_STATIC
    memkill(_MIPP_ mem,4);
#else
    memset(mem,0,MR_BIG_RESERVE(4));
#endif
    err=mr_mip->ERNUM;

    mirexit(_MIPPO_ );
    if (err==MR_ERR_OUT_OF_MEMORY) return MR_P1363_OUT_OF_MEMORY;
    if (err==MR_ERR_DIV_BY_ZERO) return MR_P1363_DIV_BY_ZERO;
    if (err!=0) return -(1000+err);
    return res;
}

/* Calculate a public/private DL key pair. W=g^S mod p 
 * where S is the private key and W the public key 
 * If RNG is NULL then the private key is provided externally in S
 * otherwise it is generated randomly internally
 */

P1363_API int DL_KEY_PAIR_GENERATE(BOOL (*idle)(void),dl_domain *DOM,csprng *RNG, octet *S,octet *W)
{
    miracl *mr_mip=mirsys(DOM->words,0);
    big q,r,g,s,w;
    int err,res=0;
#ifndef MR_STATIC
    char *mem;
#else
    char mem[MR_BIG_RESERVE(5)];
    memset(mem,0,MR_BIG_RESERVE(5));
#endif

    if (mr_mip==NULL) return MR_P1363_OUT_OF_MEMORY;
    mr_mip->ERCON=TRUE;
    set_user_function(_MIPP_ idle);
#ifndef MR_STATIC
    mem=memalloc(_MIPP_ 5);
    if (mem==NULL) res=MR_P1363_OUT_OF_MEMORY;
#endif
    if (res==0)
    {
        q=mirvar_mem(_MIPP_ mem,0);
        r=mirvar_mem(_MIPP_ mem,1);
        g=mirvar_mem(_MIPP_ mem,2);
        s=mirvar_mem(_MIPP_ mem,3);
        w=mirvar_mem(_MIPP_ mem,4);

        OS2FEP(_MIPP_ &DOM->Q,q);
        OS2FEP(_MIPP_ &DOM->R,r);
        OS2FEP(_MIPP_ &DOM->G,g);
        if (RNG!=NULL)
        {
            strong_bigrand(_MIPP_ RNG,r,s);
        }
        else
        {
            OS2FEP(_MIPP_ S,s);
            divide(_MIPP_ s,r,r);
        }
        if (DOM->PC.store==0) 
            powmod(_MIPP_ g,s,q,w);
        else
            pow_brick(_MIPP_ &DOM->PC,s,w);

        if (RNG!=NULL) convert_big_octet(_MIPP_ s,S);
        FE2OSP(_MIPP_ w,DOM->fsize,W);
    }
#ifndef MR_STATIC
    memkill(_MIPP_ mem,5);
#else
    memset(mem,0,MR_BIG_RESERVE(5));
#endif
    err=mr_mip->ERNUM;
    mirexit(_MIPPO_ );
    if (err==MR_ERR_OUT_OF_MEMORY) return MR_P1363_OUT_OF_MEMORY;
    if (err==MR_ERR_DIV_BY_ZERO) return MR_P1363_DIV_BY_ZERO;
    if (err!=0) return -(1000+err);
    return res;
}

/* validate a DL public key. Set full=TRUE for fuller, 
 * but more time-consuming test */

P1363_API int DL_PUBLIC_KEY_VALIDATE(BOOL (*idle)(void),dl_domain *DOM,BOOL full,octet *W)
{
    miracl *mr_mip=mirsys(DOM->words,0);
    big q,r,w,t;
    int err,res=0;
#ifndef MR_STATIC
    char *mem;
#else
    char mem[MR_BIG_RESERVE(4)];
    memset(mem,0,MR_BIG_RESERVE(4));
#endif

    if (mr_mip==NULL) return MR_P1363_OUT_OF_MEMORY;
    mr_mip->ERCON=TRUE;
    set_user_function(_MIPP_ idle);
#ifndef MR_STATIC
    mem=memalloc(_MIPP_ 4);
    if (mem==NULL) res=MR_P1363_OUT_OF_MEMORY;
#endif
    if (res==0)
    {
        q=mirvar_mem(_MIPP_ mem,0);
        r=mirvar_mem(_MIPP_ mem,1);
        w=mirvar_mem(_MIPP_ mem,2);
        t=mirvar_mem(_MIPP_ mem,3);

        OS2FEP(_MIPP_ &DOM->Q,q);
        OS2FEP(_MIPP_ &DOM->R,r);
        OS2FEP(_MIPP_ W,w);
        if (size(w)<2 || compare(w,q)>=0) res=MR_P1363_INVALID_PUBLIC_KEY;
    }
    if (res==0 && full) 
    {
        powmod(_MIPP_ w,r,q,t);
        if (size(t)!=1) res=MR_P1363_INVALID_PUBLIC_KEY;
    }   
#ifndef MR_STATIC
    memkill(_MIPP_ mem,4);
#else
    memset(mem,0,MR_BIG_RESERVE(4));
#endif
    err=mr_mip->ERNUM;
    mirexit(_MIPPO_ );
    if (err==MR_ERR_OUT_OF_MEMORY) return MR_P1363_OUT_OF_MEMORY;
    if (err==MR_ERR_DIV_BY_ZERO) return MR_P1363_DIV_BY_ZERO;
    if (err!=0) return -(1000+err);
    return res;
}

/*** P1363 DL primitives ***/
/* See P1363 documentation for specification */

P1363_API int DLSVDP_DH(BOOL (*idle)(void),dl_domain *DOM,octet *S,octet *WD,octet *Z) 
{
    miracl *mr_mip=mirsys(DOM->words,0);
    big q,s,wd,z;
    int err,res=0;
#ifndef MR_STATIC
    char *mem;
#else
    char mem[MR_BIG_RESERVE(4)];
    memset(mem,0,MR_BIG_RESERVE(4));
#endif

    if (mr_mip==NULL) return MR_P1363_OUT_OF_MEMORY;
    mr_mip->ERCON=TRUE;
    set_user_function(_MIPP_ idle);
#ifndef MR_STATIC
    mem=memalloc(_MIPP_ 4);
    if (mem==NULL) res=MR_P1363_OUT_OF_MEMORY;
#endif
    if (res==0)
    {
        q=mirvar_mem(_MIPP_ mem,0);
        s=mirvar_mem(_MIPP_ mem,1);
        wd=mirvar_mem(_MIPP_ mem,2);
        z=mirvar_mem(_MIPP_ mem,3);

        OS2FEP(_MIPP_ &DOM->Q,q);
        OS2FEP(_MIPP_ S,s);
        OS2FEP(_MIPP_ WD,wd);

        powmod(_MIPP_ wd,s,q,z);

        FE2OSP(_MIPP_ z,DOM->fsize,Z);
    }
#ifndef MR_STATIC
    memkill(_MIPP_ mem,4);
#else
    memset(mem,0,MR_BIG_RESERVE(4));
#endif
    err=mr_mip->ERNUM;

    mirexit(_MIPPO_ );
    if (err==MR_ERR_OUT_OF_MEMORY) return MR_P1363_OUT_OF_MEMORY;
    if (err==MR_ERR_DIV_BY_ZERO) return MR_P1363_DIV_BY_ZERO;
    if (err!=0) return -(1000+err);
    return res;
}

P1363_API int DLSVDP_DHC(BOOL (*idle)(void),dl_domain *DOM,octet *S,octet *WD,BOOL compatible,octet *Z)
{
    miracl *mr_mip=mirsys(DOM->words,0);
    big q,r,k,ik,s,wd,t,z;
    int sz;
    int err,res=0;
#ifndef MR_STATIC
    char *mem;
#else
    char mem[MR_BIG_RESERVE(8)];
    memset(mem,0,MR_BIG_RESERVE(8));
#endif


    if (mr_mip==NULL) return MR_P1363_OUT_OF_MEMORY;
    mr_mip->ERCON=TRUE;
    set_user_function(_MIPP_ idle);
#ifndef MR_STATIC
    mem=memalloc(_MIPP_ 8);
    if (mem==NULL) res=MR_P1363_OUT_OF_MEMORY;
#endif
    if (res==0)
    {
        q=mirvar_mem(_MIPP_ mem,0);
        r=mirvar_mem(_MIPP_ mem,1);
        k=mirvar_mem(_MIPP_ mem,2);
        ik=mirvar_mem(_MIPP_ mem,3);
        s=mirvar_mem(_MIPP_ mem,4);
        wd=mirvar_mem(_MIPP_ mem,5);
        z=mirvar_mem(_MIPP_ mem,6);
        t=mirvar_mem(_MIPP_ mem,7);

        OS2FEP(_MIPP_ &DOM->Q,q);
        OS2FEP(_MIPP_ &DOM->R,r);
        OS2FEP(_MIPP_ &DOM->K,k);
        OS2FEP(_MIPP_ S,s);
        OS2FEP(_MIPP_ WD,wd);

        if (compatible)
        {
            OS2FEP(_MIPP_ &DOM->IK,ik);
            mad(_MIPP_ ik,s,ik,r,r,t);   /* t=s/k mod r */
        }
        else copy(s,t);
        multiply(_MIPP_ t,k,t);        /* kt */
        powmod(_MIPP_ wd,t,q,z);

        sz=size(z);
        if (sz==0 || sz==1) res=MR_P1363_INVALID_PUBLIC_KEY;
        else FE2OSP(_MIPP_ z,DOM->fsize,Z);
    }
#ifndef MR_STATIC
    memkill(_MIPP_ mem,8);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -