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

📄 montexpo.c

📁 应用密码学这本书的源代码
💻 C
字号:
/*

  Author:  Pate Williams (c) 1997



  Montgomery exponentiation. See "Handbook of Applied

  Cryptography" by Alfred J. Menezes et al Section

  14.6.1 pages 614 - 620.

*/



#include <stdio.h>

#include <stdlib.h>

#include "lip.h"



#define DEBUG



void radix_representation(long b, long n, long *a, verylong za)

{

  long i = 0;

  verylong zb = 0, zq = 0, zr = 0, zx = 0;



  zintoz(b, &zb);

  zcopy(za, &zx);

  do {

    zdiv(zx, zb, &zq, &zr);

    a[i++] = ztoint(zr);

    zcopy(zq, &zx);

  } while (zscompare(zq, 0l) != 0);

  while (i < n) a[i++] = 0;

  zfree(&zb);

  zfree(&zq);

  zfree(&zr);

  zfree(&zx);

}



void Montgomery_multiplication(long b, long n,

                               verylong zm, verylong zx,

                               verylong zy, verylong *zA)

{

  long i, n1 = n + 1, u, mp, *a, *m, *x, *y;

  verylong za = 0, zb = 0, zc = 0, zd = 0, zs = 0;



  a = calloc(n1, sizeof(long));

  m = calloc(n1, sizeof(long));

  x = calloc(n1, sizeof(long));

  y = calloc(n1, sizeof(long));

  if (a == 0 || m == 0 || x == 0 || y == 0) {

    printf("*error*\ncan't get memory from Montgomery");

    printf(" multiplication");

    exit(1);

  }

  zintoz(b, &zb);

  zinvmod(zm, zb, &za);

  znegate(&za);

  mp = zsmod(za, b);

  radix_representation(b, n1, m, zm);

  radix_representation(b, n1, x, zx);

  radix_representation(b, n1, y, zy);

  zzero(zA);

  for (i = 0; i < n; i++) {

    radix_representation(b, n1, a, *zA);

    u = ((a[0] + x[i] * y[0]) * mp) % b;

    zsmul(zy, x[i], &za);

    zsmul(zm, u, &zc);

    zadd(*zA, za, &zs);

    zadd(zs, zc, &zd);

    zsdiv(zd, b, zA);

  }

  if (zcompare(*zA, zm) >= 0) {

    zsub(*zA, zm, &za);

    zcopy(za, zA);

  }

  free(a);

  free(m);

  free(x);

  free(y);

  zfree(&za);

  zfree(&zb);

  zfree(&zc);

  zfree(&zd);

  zfree(&zs);

}



void Montgomery_exponentiation(char *e, long b, long l, long t,

                               verylong zR, verylong zm,

                               verylong zx, verylong *zA)

{

  long i;

  verylong za = 0, zb = 0, zxp = 0;



  zmulmod(zR, zR, zm, &zb);

  Montgomery_multiplication(b, l, zm, zx, zb, &zxp);

  zmod(zR, zm, zA);

  for (i = t; i >= 0; i--) {

    Montgomery_multiplication(b, l, zm, *zA, *zA, &za);

    zcopy(za, zA);

    if (e[i] == 1) {

      Montgomery_multiplication(b, l, zm , *zA, zxp, &za);

      zcopy(za, zA);

    }

    #ifdef DEBUG

    zwriteln(*zA);

    #endif

  }

  zone(&zxp);

  Montgomery_multiplication(b, l, zm, *zA, zxp, &za);

  zcopy(za, zA);

  zfree(&za);

  zfree(&zb);

  zfree(&zxp);

}



int main(void)

{

  char e[4] = {1, 1, 0, 1};

  long b = 10, l = 5, t = 3;

  verylong zA = 0, zR = 0, za = 0, zm = 0, zx = 0;



  zintoz(100000l, &zR);

  zintoz(72639l, &zm);

  zintoz(5792l, &zx);

  Montgomery_exponentiation(e, b, l, t, zR, zm, zx, &zA);

  zsexpmod(zx, 11, zm, &za);

  zwriteln(za);

  zwriteln(zA);

  zfree(&zA);

  zfree(&zR);

  zfree(&za);

  zfree(&zm);

  zfree(&zx);

  return 0;

}

⌨️ 快捷键说明

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