Back to index

lightning-sunbird  0.9+nobinonly
Classes | Defines | Typedefs | Functions
mpi.h File Reference
#include "mpi-config.h"
#include <limits.h>
#include <sys/types.h>

Go to the source code of this file.

Classes

struct  mp_int

Defines

#define MP_NEG   1
#define MP_ZPOS   0
#define MP_OKAY   0 /* no error, all is well */
#define MP_YES   0 /* yes (boolean result) */
#define MP_NO   -1 /* no (boolean result) */
#define MP_MEM   -2 /* out of memory */
#define MP_RANGE   -3 /* argument out of range */
#define MP_BADARG   -4 /* invalid parameter */
#define MP_UNDEF   -5 /* answer is undefined */
#define MP_LAST_CODE   MP_UNDEF
#define MP_32BIT_MAX   4294967295U
#define MP_DIGIT_MAX   UINT_MAX
#define MP_DIGIT_FMT   "%08X" /* printf() format for 1 digit */
#define MP_HALF_DIGIT_MAX   USHRT_MAX
#define MP_USE_UINT_DIGIT   1
#define MP_NO_MP_WORD   1
#define MP_DIGIT_BIT   (CHAR_BIT*sizeof(mp_digit))
#define MP_WORD_BIT   (CHAR_BIT*sizeof(mp_word))
#define MP_RADIX   (1+(mp_word)MP_DIGIT_MAX)
#define MP_HALF_DIGIT_BIT   (MP_DIGIT_BIT/2)
#define MP_HALF_RADIX   (1+(mp_digit)MP_HALF_DIGIT_MAX)
#define MP_SIGN(MP)   ((MP)->sign)
#define MP_USED(MP)   ((MP)->used)
#define MP_ALLOC(MP)   ((MP)->alloc)
#define MP_DIGITS(MP)   ((MP)->dp)
#define MP_DIGIT(MP, N)   (MP)->dp[(N)]
#define MP_MAX_RADIX   64
#define mp_set_long(mp, z)   mp_set_int(mp,z)
#define mp_tobinary(M, S)   mp_toradix((M), (S), 2)
#define mp_tooctal(M, S)   mp_toradix((M), (S), 8)
#define mp_todecimal(M, S)   mp_toradix((M), (S), 10)
#define mp_tohex(M, S)   mp_toradix((M), (S), 16)
#define MP_CHECKOK(x)   if (MP_OKAY > (res = (x))) goto CLEANUP
#define MP_CHECKERR(x)   if (MP_OKAY > (res = (x))) goto CLEANUP

Typedefs

typedef unsigned int mp_sign
typedef unsigned int mp_size
typedef int mp_err
typedef unsigned int mp_digit

Functions

mp_size mp_get_prec (void)
void mp_set_prec (mp_size prec)
mp_err mp_init (mp_int *mp)
mp_err mp_init_size (mp_int *mp, mp_size prec)
mp_err mp_init_copy (mp_int *mp, const mp_int *from)
mp_err mp_copy (const mp_int *from, mp_int *to)
void mp_exch (mp_int *mp1, mp_int *mp2)
void mp_clear (mp_int *mp)
void mp_zero (mp_int *mp)
void mp_set (mp_int *mp, mp_digit d)
mp_err mp_set_int (mp_int *mp, long z)
mp_err mp_set_ulong (mp_int *mp, unsigned long z)
mp_err mp_add_d (const mp_int *a, mp_digit d, mp_int *b)
mp_err mp_sub_d (const mp_int *a, mp_digit d, mp_int *b)
mp_err mp_mul_d (const mp_int *a, mp_digit d, mp_int *b)
mp_err mp_mul_2 (const mp_int *a, mp_int *c)
mp_err mp_div_d (const mp_int *a, mp_digit d, mp_int *q, mp_digit *r)
mp_err mp_div_2 (const mp_int *a, mp_int *c)
mp_err mp_expt_d (const mp_int *a, mp_digit d, mp_int *c)
mp_err mp_abs (const mp_int *a, mp_int *b)
mp_err mp_neg (const mp_int *a, mp_int *b)
mp_err mp_add (const mp_int *a, const mp_int *b, mp_int *c)
mp_err mp_sub (const mp_int *a, const mp_int *b, mp_int *c)
mp_err mp_mul (const mp_int *a, const mp_int *b, mp_int *c)
mp_err mp_sqr (const mp_int *a, mp_int *b)
mp_err mp_div (const mp_int *a, const mp_int *b, mp_int *q, mp_int *r)
mp_err mp_div_2d (const mp_int *a, mp_digit d, mp_int *q, mp_int *r)
mp_err mp_expt (mp_int *a, mp_int *b, mp_int *c)
mp_err mp_2expt (mp_int *a, mp_digit k)
mp_err mp_sqrt (const mp_int *a, mp_int *b)
mp_err mp_mod (const mp_int *a, const mp_int *m, mp_int *c)
mp_err mp_mod_d (const mp_int *a, mp_digit d, mp_digit *c)
mp_err mp_addmod (const mp_int *a, const mp_int *b, const mp_int *m, mp_int *c)
mp_err mp_submod (const mp_int *a, const mp_int *b, const mp_int *m, mp_int *c)
mp_err mp_mulmod (const mp_int *a, const mp_int *b, const mp_int *m, mp_int *c)
mp_err mp_sqrmod (const mp_int *a, const mp_int *m, mp_int *c)
mp_err mp_exptmod (const mp_int *a, const mp_int *b, const mp_int *m, mp_int *c)
mp_err mp_exptmod_d (const mp_int *a, mp_digit d, const mp_int *m, mp_int *c)
int mp_cmp_z (const mp_int *a)
int mp_cmp_d (const mp_int *a, mp_digit d)
int mp_cmp (const mp_int *a, const mp_int *b)
int mp_cmp_mag (mp_int *a, mp_int *b)
int mp_cmp_int (const mp_int *a, long z)
int mp_isodd (const mp_int *a)
int mp_iseven (const mp_int *a)
mp_err mp_gcd (mp_int *a, mp_int *b, mp_int *c)
mp_err mp_lcm (mp_int *a, mp_int *b, mp_int *c)
mp_err mp_xgcd (const mp_int *a, const mp_int *b, mp_int *g, mp_int *x, mp_int *y)
mp_err mp_invmod (const mp_int *a, const mp_int *m, mp_int *c)
mp_err mp_invmod_xgcd (const mp_int *a, const mp_int *m, mp_int *c)
mp_err mp_read_raw (mp_int *mp, char *str, int len)
int mp_raw_size (mp_int *mp)
mp_err mp_toraw (mp_int *mp, char *str)
mp_err mp_read_radix (mp_int *mp, const char *str, int radix)
mp_err mp_read_variable_radix (mp_int *a, const char *str, int default_radix)
int mp_radix_size (mp_int *mp, int radix)
mp_err mp_toradix (mp_int *mp, char *str, int radix)
int mp_tovalue (char ch, int r)
const char * mp_strerror (mp_err ec)
mp_err mp_read_unsigned_octets (mp_int *mp, const unsigned char *str, mp_size len)
int mp_unsigned_octet_size (const mp_int *mp)
mp_err mp_to_unsigned_octets (const mp_int *mp, unsigned char *str, mp_size maxlen)
mp_err mp_to_signed_octets (const mp_int *mp, unsigned char *str, mp_size maxlen)
mp_err mp_to_fixlen_octets (const mp_int *mp, unsigned char *str, mp_size len)
mp_size mp_trailing_zeros (const mp_int *mp)

Class Documentation

struct mp_int

Definition at line 190 of file mpi.h.

Class Members
mp_size alloc
mp_digit * dp
mp_sign sign
mp_size used

Define Documentation

#define MP_32BIT_MAX   4294967295U

Definition at line 89 of file mpi.h.

#define MP_ALLOC (   MP)    ((MP)->alloc)

Definition at line 183 of file mpi.h.

#define MP_BADARG   -4 /* invalid parameter */

Definition at line 81 of file mpi.h.

#define MP_CHECKERR (   x)    if (MP_OKAY > (res = (x))) goto CLEANUP

Definition at line 310 of file mpi.h.

#define MP_CHECKOK (   x)    if (MP_OKAY > (res = (x))) goto CLEANUP

Definition at line 309 of file mpi.h.

#define MP_DIGIT (   MP,
  N 
)    (MP)->dp[(N)]

Definition at line 185 of file mpi.h.

#define MP_DIGIT_BIT   (CHAR_BIT*sizeof(mp_digit))

Definition at line 168 of file mpi.h.

#define MP_DIGIT_FMT   "%08X" /* printf() format for 1 digit */

Definition at line 134 of file mpi.h.

#define MP_DIGIT_MAX   UINT_MAX

Definition at line 133 of file mpi.h.

#define MP_DIGITS (   MP)    ((MP)->dp)

Definition at line 184 of file mpi.h.

Definition at line 172 of file mpi.h.

Definition at line 135 of file mpi.h.

Definition at line 173 of file mpi.h.

Definition at line 83 of file mpi.h.

#define MP_MAX_RADIX   64

Definition at line 188 of file mpi.h.

#define MP_MEM   -2 /* out of memory */

Definition at line 79 of file mpi.h.

#define MP_NEG   1

Definition at line 73 of file mpi.h.

#define MP_NO   -1 /* no (boolean result) */

Definition at line 78 of file mpi.h.

Definition at line 158 of file mpi.h.

#define MP_OKAY   0 /* no error, all is well */

Definition at line 76 of file mpi.h.

#define MP_RADIX   (1+(mp_word)MP_DIGIT_MAX)

Definition at line 170 of file mpi.h.

#define MP_RANGE   -3 /* argument out of range */

Definition at line 80 of file mpi.h.

#define mp_set_long (   mp,
 
)    mp_set_int(mp,z)

Definition at line 211 of file mpi.h.

#define MP_SIGN (   MP)    ((MP)->sign)

Definition at line 181 of file mpi.h.

#define mp_tobinary (   M,
  S 
)    mp_toradix((M), (S), 2)

Definition at line 291 of file mpi.h.

#define mp_todecimal (   M,
  S 
)    mp_toradix((M), (S), 10)

Definition at line 293 of file mpi.h.

#define mp_tohex (   M,
  S 
)    mp_toradix((M), (S), 16)

Definition at line 294 of file mpi.h.

#define mp_tooctal (   M,
  S 
)    mp_toradix((M), (S), 8)

Definition at line 292 of file mpi.h.

#define MP_UNDEF   -5 /* answer is undefined */

Definition at line 82 of file mpi.h.

Definition at line 137 of file mpi.h.

#define MP_USED (   MP)    ((MP)->used)

Definition at line 182 of file mpi.h.

#define MP_WORD_BIT   (CHAR_BIT*sizeof(mp_word))

Definition at line 169 of file mpi.h.

#define MP_YES   0 /* yes (boolean result) */

Definition at line 77 of file mpi.h.

#define MP_ZPOS   0

Definition at line 74 of file mpi.h.


Typedef Documentation

typedef unsigned int mp_digit

Definition at line 132 of file mpi.h.

typedef int mp_err

Definition at line 87 of file mpi.h.

typedef unsigned int mp_sign

Definition at line 85 of file mpi.h.

typedef unsigned int mp_size

Definition at line 86 of file mpi.h.


Function Documentation

mp_err mp_2expt ( mp_int a,
mp_digit  k 
)

Definition at line 1192 of file mpi.c.

{
  ARGCHK(a != NULL, MP_BADARG);

  return s_mp_2expt(a, k);

} /* end mp_2expt() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_abs ( const mp_int a,
mp_int b 
)

Definition at line 687 of file mpi.c.

{
  mp_err   res;

  ARGCHK(a != NULL && b != NULL, MP_BADARG);

  if((res = mp_copy(a, b)) != MP_OKAY)
    return res;

  SIGN(b) = ZPOS;

  return MP_OKAY;

} /* end mp_abs() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_add ( const mp_int a,
const mp_int b,
mp_int c 
)

Definition at line 740 of file mpi.c.

{
  mp_err  res;

  ARGCHK(a != NULL && b != NULL && c != NULL, MP_BADARG);

  if(SIGN(a) == SIGN(b)) { /* same sign:  add values, keep sign */
    MP_CHECKOK( s_mp_add_3arg(a, b, c) );
  } else if(s_mp_cmp(a, b) >= 0) {  /* different sign: |a| >= |b|   */
    MP_CHECKOK( s_mp_sub_3arg(a, b, c) );
  } else {                          /* different sign: |a|  < |b|   */
    MP_CHECKOK( s_mp_sub_3arg(b, a, c) );
  }

  if (s_mp_cmp_d(c, 0) == MP_EQ)
    SIGN(c) = ZPOS;

CLEANUP:
  return res;

} /* end mp_add() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_add_d ( const mp_int a,
mp_digit  d,
mp_int b 
)

Definition at line 419 of file mpi.c.

{
  mp_int   tmp;
  mp_err   res;

  ARGCHK(a != NULL && b != NULL, MP_BADARG);

  if((res = mp_init_copy(&tmp, a)) != MP_OKAY)
    return res;

  if(SIGN(&tmp) == ZPOS) {
    if((res = s_mp_add_d(&tmp, d)) != MP_OKAY)
      goto CLEANUP;
  } else if(s_mp_cmp_d(&tmp, d) >= 0) {
    if((res = s_mp_sub_d(&tmp, d)) != MP_OKAY)
      goto CLEANUP;
  } else {
    mp_neg(&tmp, &tmp);

    DIGIT(&tmp, 0) = d - DIGIT(&tmp, 0);
  }

  if(s_mp_cmp_d(&tmp, 0) == 0)
    SIGN(&tmp) = ZPOS;

  s_mp_exch(&tmp, b);

CLEANUP:
  mp_clear(&tmp);
  return res;

} /* end mp_add_d() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_addmod ( const mp_int a,
const mp_int b,
const mp_int m,
mp_int c 
)

Definition at line 1393 of file mpi.c.

{
  mp_err  res;

  ARGCHK(a != NULL && b != NULL && m != NULL && c != NULL, MP_BADARG);

  if((res = mp_add(a, b, c)) != MP_OKAY)
    return res;
  if((res = mp_mod(c, m, c)) != MP_OKAY)
    return res;

  return MP_OKAY;

}

Here is the call graph for this function:

Here is the caller graph for this function:

void mp_clear ( mp_int mp)

Definition at line 287 of file mpi.c.

{
  if(mp == NULL)
    return;

  if(DIGITS(mp) != NULL) {
#if MP_CRYPTO
    s_mp_setz(DIGITS(mp), ALLOC(mp));
#endif
    s_mp_free(DIGITS(mp));
    DIGITS(mp) = NULL;
  }

  USED(mp) = 0;
  ALLOC(mp) = 0;

} /* end mp_clear() */

Here is the call graph for this function:

int mp_cmp ( const mp_int a,
const mp_int b 
)

Definition at line 1671 of file mpi.c.

{
  ARGCHK(a != NULL && b != NULL, MP_EQ);

  if(SIGN(a) == SIGN(b)) {
    int  mag;

    if((mag = s_mp_cmp(a, b)) == MP_EQ)
      return MP_EQ;

    if(SIGN(a) == ZPOS)
      return mag;
    else
      return -mag;

  } else if(SIGN(a) == ZPOS) {
    return MP_GT;
  } else {
    return MP_LT;
  }

} /* end mp_cmp() */

Here is the call graph for this function:

int mp_cmp_d ( const mp_int a,
mp_digit  d 
)

Definition at line 1656 of file mpi.c.

{
  ARGCHK(a != NULL, MP_EQ);

  if(SIGN(a) == NEG)
    return MP_LT;

  return s_mp_cmp_d(a, d);

} /* end mp_cmp_d() */

Here is the call graph for this function:

Here is the caller graph for this function:

int mp_cmp_int ( const mp_int a,
long  z 
)

Definition at line 1722 of file mpi.c.

{
  mp_int  tmp;
  int     out;

  ARGCHK(a != NULL, MP_EQ);
  
  mp_init(&tmp); mp_set_int(&tmp, z);
  out = mp_cmp(a, &tmp);
  mp_clear(&tmp);

  return out;

} /* end mp_cmp_int() */

Here is the call graph for this function:

Here is the caller graph for this function:

int mp_cmp_mag ( mp_int a,
mp_int b 
)

Definition at line 1704 of file mpi.c.

{
  ARGCHK(a != NULL && b != NULL, MP_EQ);

  return s_mp_cmp(a, b);

} /* end mp_cmp_mag() */

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 1635 of file mpi.c.

{
  if(SIGN(a) == NEG)
    return MP_LT;
  else if(USED(a) == 1 && DIGIT(a, 0) == 0)
    return MP_EQ;
  else
    return MP_GT;

} /* end mp_cmp_z() */
mp_err mp_copy ( const mp_int from,
mp_int to 
)

Definition at line 202 of file mpi.c.

{
  ARGCHK(from != NULL && to != NULL, MP_BADARG);

  if(from == to)
    return MP_OKAY;

  ++mp_copies;
  { /* copy */
    mp_digit   *tmp;

    /*
      If the allocated buffer in 'to' already has enough space to hold
      all the used digits of 'from', we'll re-use it to avoid hitting
      the memory allocater more than necessary; otherwise, we'd have
      to grow anyway, so we just allocate a hunk and make the copy as
      usual
     */
    if(ALLOC(to) >= USED(from)) {
      s_mp_setz(DIGITS(to) + USED(from), ALLOC(to) - USED(from));
      s_mp_copy(DIGITS(from), DIGITS(to), USED(from));
      
    } else {
      if((tmp = s_mp_alloc(ALLOC(from), sizeof(mp_digit))) == NULL)
       return MP_MEM;

      s_mp_copy(DIGITS(from), tmp, USED(from));

      if(DIGITS(to) != NULL) {
#if MP_CRYPTO
       s_mp_setz(DIGITS(to), ALLOC(to));
#endif
       s_mp_free(DIGITS(to));
      }

      DIGITS(to) = tmp;
      ALLOC(to) = ALLOC(from);
    }

    /* Copy the precision and sign from the original */
    USED(to) = USED(from);
    SIGN(to) = SIGN(from);
  } /* end copy */

  return MP_OKAY;

} /* end mp_copy() */

Here is the call graph for this function:

mp_err mp_div ( const mp_int a,
const mp_int b,
mp_int q,
mp_int r 
)

Definition at line 1000 of file mpi.c.

{
  mp_err   res;
  mp_int   *pQ, *pR;
  mp_int   qtmp, rtmp, btmp;
  int      cmp;
  mp_sign  signA = MP_SIGN(a);
  mp_sign  signB = MP_SIGN(b);

  ARGCHK(a != NULL && b != NULL, MP_BADARG);

  if(mp_cmp_z(b) == MP_EQ)
    return MP_RANGE;

  DIGITS(&qtmp) = 0;
  DIGITS(&rtmp) = 0;
  DIGITS(&btmp) = 0;

  /* Set up some temporaries... */
  if (!r || r == a || r == b) {
    MP_CHECKOK( mp_init_copy(&rtmp, a) );
    pR = &rtmp;
  } else {
    MP_CHECKOK( mp_copy(a, r) );
    pR = r;
  }

  if (!q || q == a || q == b) {
    MP_CHECKOK( mp_init_size(&qtmp, MP_USED(a)) );
    pQ = &qtmp;
  } else {
    MP_CHECKOK( s_mp_pad(q, MP_USED(a)) );
    pQ = q;
    mp_zero(pQ);
  }

  /*
    If |a| <= |b|, we can compute the solution without division;
    otherwise, we actually do the work required.
   */
  if ((cmp = s_mp_cmp(a, b)) <= 0) {
    if (cmp) {
      /* r was set to a above. */
      mp_zero(pQ);
    } else {
      mp_set(pQ, 1);
      mp_zero(pR);
    }
  } else {
    MP_CHECKOK( mp_init_copy(&btmp, b) );
    MP_CHECKOK( s_mp_div(pR, &btmp, pQ) );
  }

  /* Compute the signs for the output  */
  MP_SIGN(pR) = signA;   /* Sr = Sa              */
  /* Sq = ZPOS if Sa == Sb */ /* Sq = NEG if Sa != Sb */
  MP_SIGN(pQ) = (signA == signB) ? ZPOS : NEG;

  if(s_mp_cmp_d(pQ, 0) == MP_EQ)
    SIGN(pQ) = ZPOS;
  if(s_mp_cmp_d(pR, 0) == MP_EQ)
    SIGN(pR) = ZPOS;

  /* Copy output, if it is needed      */
  if(q && q != pQ) 
    s_mp_exch(pQ, q);

  if(r && r != pR) 
    s_mp_exch(pR, r);

CLEANUP:
  mp_clear(&btmp);
  mp_clear(&rtmp);
  mp_clear(&qtmp);

  return res;

} /* end mp_div() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_div_2 ( const mp_int a,
mp_int c 
)

Definition at line 616 of file mpi.c.

{
  mp_err  res;

  ARGCHK(a != NULL && c != NULL, MP_BADARG);

  if((res = mp_copy(a, c)) != MP_OKAY)
    return res;

  s_mp_div_2(c);

  return MP_OKAY;

} /* end mp_div_2() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_div_2d ( const mp_int a,
mp_digit  d,
mp_int q,
mp_int r 
)

Definition at line 1083 of file mpi.c.

{
  mp_err  res;

  ARGCHK(a != NULL, MP_BADARG);

  if(q) {
    if((res = mp_copy(a, q)) != MP_OKAY)
      return res;
  }
  if(r) {
    if((res = mp_copy(a, r)) != MP_OKAY)
      return res;
  }
  if(q) {
    s_mp_div_2d(q, d);
  }
  if(r) {
    s_mp_mod_2d(r, d);
  }

  return MP_OKAY;

} /* end mp_div_2d() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_div_d ( const mp_int a,
mp_digit  d,
mp_int q,
mp_digit r 
)

Definition at line 557 of file mpi.c.

{
  mp_err   res;
  mp_int   qp;
  mp_digit rem;
  int      pow;

  ARGCHK(a != NULL, MP_BADARG);

  if(d == 0)
    return MP_RANGE;

  /* Shortcut for powers of two ... */
  if((pow = s_mp_ispow2d(d)) >= 0) {
    mp_digit  mask;

    mask = ((mp_digit)1 << pow) - 1;
    rem = DIGIT(a, 0) & mask;

    if(q) {
      mp_copy(a, q);
      s_mp_div_2d(q, pow);
    }

    if(r)
      *r = rem;

    return MP_OKAY;
  }

  if((res = mp_init_copy(&qp, a)) != MP_OKAY)
    return res;

  res = s_mp_div_d(&qp, d, &rem);

  if(s_mp_cmp_d(&qp, 0) == 0)
    SIGN(q) = ZPOS;

  if(r)
    *r = rem;

  if(q)
    s_mp_exch(&qp, q);

  mp_clear(&qp);
  return res;

} /* end mp_div_d() */

Here is the call graph for this function:

Here is the caller graph for this function:

void mp_exch ( mp_int mp1,
mp_int mp2 
)

Definition at line 262 of file mpi.c.

{
#if MP_ARGCHK == 2
  assert(mp1 != NULL && mp2 != NULL);
#else
  if(mp1 == NULL || mp2 == NULL)
    return;
#endif

  s_mp_exch(mp1, mp2);

} /* end mp_exch() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_expt ( mp_int a,
mp_int b,
mp_int c 
)

Definition at line 1119 of file mpi.c.

{
  mp_int   s, x;
  mp_err   res;
  mp_digit d;
  int      dig, bit;

  ARGCHK(a != NULL && b != NULL && c != NULL, MP_BADARG);

  if(mp_cmp_z(b) < 0)
    return MP_RANGE;

  if((res = mp_init(&s)) != MP_OKAY)
    return res;

  mp_set(&s, 1);

  if((res = mp_init_copy(&x, a)) != MP_OKAY)
    goto X;

  /* Loop over low-order digits in ascending order */
  for(dig = 0; dig < (USED(b) - 1); dig++) {
    d = DIGIT(b, dig);

    /* Loop over bits of each non-maximal digit */
    for(bit = 0; bit < DIGIT_BIT; bit++) {
      if(d & 1) {
       if((res = s_mp_mul(&s, &x)) != MP_OKAY) 
         goto CLEANUP;
      }

      d >>= 1;
      
      if((res = s_mp_sqr(&x)) != MP_OKAY)
       goto CLEANUP;
    }
  }

  /* Consider now the last digit... */
  d = DIGIT(b, dig);

  while(d) {
    if(d & 1) {
      if((res = s_mp_mul(&s, &x)) != MP_OKAY)
       goto CLEANUP;
    }

    d >>= 1;

    if((res = s_mp_sqr(&x)) != MP_OKAY)
      goto CLEANUP;
  }
  
  if(mp_iseven(b))
    SIGN(&s) = SIGN(a);

  res = mp_copy(&s, c);

CLEANUP:
  mp_clear(&x);
X:
  mp_clear(&s);

  return res;

} /* end mp_expt() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_expt_d ( const mp_int a,
mp_digit  d,
mp_int c 
)

Definition at line 635 of file mpi.c.

{
  mp_int   s, x;
  mp_err   res;

  ARGCHK(a != NULL && c != NULL, MP_BADARG);

  if((res = mp_init(&s)) != MP_OKAY)
    return res;
  if((res = mp_init_copy(&x, a)) != MP_OKAY)
    goto X;

  DIGIT(&s, 0) = 1;

  while(d != 0) {
    if(d & 1) {
      if((res = s_mp_mul(&s, &x)) != MP_OKAY)
       goto CLEANUP;
    }

    d /= 2;

    if((res = s_mp_sqr(&x)) != MP_OKAY)
      goto CLEANUP;
  }

  s_mp_exch(&s, c);

CLEANUP:
  mp_clear(&x);
X:
  mp_clear(&s);

  return res;

} /* end mp_expt_d() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_exptmod ( const mp_int a,
const mp_int b,
const mp_int m,
mp_int c 
)

Definition at line 1080 of file mpmontg.c.

{
  const mp_int *base;
  mp_size bits_in_exponent, i, window_bits, odd_ints;
  mp_err  res;
  int     nLen;
  mp_int  montBase, goodBase;
  mp_mont_modulus mmm;
#ifdef MP_USING_CACHE_SAFE_MOD_EXP
  static unsigned int max_window_bits;
#endif

  /* function for computing n0prime only works if n0 is odd */
  if (!mp_isodd(modulus))
    return s_mp_exptmod(inBase, exponent, modulus, result);

  MP_DIGITS(&montBase) = 0;
  MP_DIGITS(&goodBase) = 0;

  if (mp_cmp(inBase, modulus) < 0) {
    base = inBase;
  } else {
    MP_CHECKOK( mp_init(&goodBase) );
    base = &goodBase;
    MP_CHECKOK( mp_mod(inBase, modulus, &goodBase) );
  }

  nLen  = MP_USED(modulus);
  MP_CHECKOK( mp_init_size(&montBase, 2 * nLen + 2) );

  mmm.N = *modulus;                /* a copy of the mp_int struct */
  i = mpl_significant_bits(modulus);
  i += MP_DIGIT_BIT - 1;
  mmm.b = i - i % MP_DIGIT_BIT;

  /* compute n0', given n0, n0' = -(n0 ** -1) mod MP_RADIX
  **          where n0 = least significant mp_digit of N, the modulus.
  */
  mmm.n0prime = 0 - s_mp_invmod_radix( MP_DIGIT(modulus, 0) );

  MP_CHECKOK( s_mp_to_mont(base, &mmm, &montBase) );

  bits_in_exponent = mpl_significant_bits(exponent);
#ifdef MP_USING_CACHE_SAFE_MOD_EXP
  if (mp_using_cache_safe_exp) {
    if (bits_in_exponent > 780)
       window_bits = 6;
    else if (bits_in_exponent > 256)
       window_bits = 5;
    else if (bits_in_exponent > 20)
       window_bits = 4;
       /* RSA public key exponents are typically under 20 bits (common values 
        * are: 3, 17, 65537) and a 4-bit window is inefficient
        */
    else 
       window_bits = 1;
  } else
#endif
  if (bits_in_exponent > 480)
    window_bits = 6;
  else if (bits_in_exponent > 160)
    window_bits = 5;
  else if (bits_in_exponent > 20)
    window_bits = 4;
  /* RSA public key exponents are typically under 20 bits (common values 
   * are: 3, 17, 65537) and a 4-bit window is inefficient
   */
  else 
    window_bits = 1;

#ifdef MP_USING_CACHE_SAFE_MOD_EXP
  /*
   * clamp the window size based on
   * the cache line size.
   */
  if (!max_window_bits) {
    unsigned long cache_size = s_mpi_getProcessorLineSize();
    /* processor has no cache, use 'fast' code always */
    if (cache_size == 0) {
      mp_using_cache_safe_exp = 0;
    } 
    if ((cache_size == 0) || (cache_size >= 64)) {
      max_window_bits = 6;
    } else if (cache_size >= 32) {
      max_window_bits = 5;
    } else if (cache_size >= 16) {
      max_window_bits = 4;
    } else max_window_bits = 1; /* should this be an assert? */
  }

  /* clamp the window size down before we caclulate bits_in_exponent */
  if (mp_using_cache_safe_exp) {
    if (window_bits > max_window_bits) {
      window_bits = max_window_bits;
    }
  }
#endif

  odd_ints = 1 << (window_bits - 1);
  i = bits_in_exponent % window_bits;
  if (i != 0) {
    bits_in_exponent += window_bits - i;
  } 

#ifdef MP_USING_MONT_MULF
  if (mp_using_mont_mulf) {
    MP_CHECKOK( s_mp_pad(&montBase, nLen) );
    res = mp_exptmod_f(&montBase, exponent, modulus, result, &mmm, nLen, 
                   bits_in_exponent, window_bits, odd_ints);
  } else
#endif
#ifdef MP_USING_CACHE_SAFE_MOD_EXP
  if (mp_using_cache_safe_exp) {
    res = mp_exptmod_safe_i(&montBase, exponent, modulus, result, &mmm, nLen, 
                   bits_in_exponent, window_bits, 1 << window_bits);
  } else
#endif
  res = mp_exptmod_i(&montBase, exponent, modulus, result, &mmm, nLen, 
                   bits_in_exponent, window_bits, odd_ints);

CLEANUP:
  mp_clear(&montBase);
  mp_clear(&goodBase);
  /* Don't mp_clear mmm.N because it is merely a copy of modulus.
  ** Just zap it.
  */
  memset(&mmm, 0, sizeof mmm);
  return res;
}

Here is the call graph for this function:

mp_err mp_exptmod_d ( const mp_int a,
mp_digit  d,
const mp_int m,
mp_int c 
)

Definition at line 1580 of file mpi.c.

{
  mp_int   s, x;
  mp_err   res;

  ARGCHK(a != NULL && c != NULL, MP_BADARG);

  if((res = mp_init(&s)) != MP_OKAY)
    return res;
  if((res = mp_init_copy(&x, a)) != MP_OKAY)
    goto X;

  mp_set(&s, 1);

  while(d != 0) {
    if(d & 1) {
      if((res = s_mp_mul(&s, &x)) != MP_OKAY ||
        (res = mp_mod(&s, m, &s)) != MP_OKAY)
       goto CLEANUP;
    }

    d /= 2;

    if((res = s_mp_sqr(&x)) != MP_OKAY ||
       (res = mp_mod(&x, m, &x)) != MP_OKAY)
      goto CLEANUP;
  }

  s_mp_exch(&s, c);

CLEANUP:
  mp_clear(&x);
X:
  mp_clear(&s);

  return res;

} /* end mp_exptmod_d() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_gcd ( mp_int a,
mp_int b,
mp_int c 
)

Definition at line 1778 of file mpi.c.

{
  mp_err   res;
  mp_int   u, v, t;
  mp_size  k = 0;

  ARGCHK(a != NULL && b != NULL && c != NULL, MP_BADARG);

  if(mp_cmp_z(a) == MP_EQ && mp_cmp_z(b) == MP_EQ)
      return MP_RANGE;
  if(mp_cmp_z(a) == MP_EQ) {
    return mp_copy(b, c);
  } else if(mp_cmp_z(b) == MP_EQ) {
    return mp_copy(a, c);
  }

  if((res = mp_init(&t)) != MP_OKAY)
    return res;
  if((res = mp_init_copy(&u, a)) != MP_OKAY)
    goto U;
  if((res = mp_init_copy(&v, b)) != MP_OKAY)
    goto V;

  SIGN(&u) = ZPOS;
  SIGN(&v) = ZPOS;

  /* Divide out common factors of 2 until at least 1 of a, b is even */
  while(mp_iseven(&u) && mp_iseven(&v)) {
    s_mp_div_2(&u);
    s_mp_div_2(&v);
    ++k;
  }

  /* Initialize t */
  if(mp_isodd(&u)) {
    if((res = mp_copy(&v, &t)) != MP_OKAY)
      goto CLEANUP;
    
    /* t = -v */
    if(SIGN(&v) == ZPOS)
      SIGN(&t) = NEG;
    else
      SIGN(&t) = ZPOS;
    
  } else {
    if((res = mp_copy(&u, &t)) != MP_OKAY)
      goto CLEANUP;

  }

  for(;;) {
    while(mp_iseven(&t)) {
      s_mp_div_2(&t);
    }

    if(mp_cmp_z(&t) == MP_GT) {
      if((res = mp_copy(&t, &u)) != MP_OKAY)
       goto CLEANUP;

    } else {
      if((res = mp_copy(&t, &v)) != MP_OKAY)
       goto CLEANUP;

      /* v = -t */
      if(SIGN(&t) == ZPOS)
       SIGN(&v) = NEG;
      else
       SIGN(&v) = ZPOS;
    }

    if((res = mp_sub(&u, &v, &t)) != MP_OKAY)
      goto CLEANUP;

    if(s_mp_cmp_d(&t, 0) == MP_EQ)
      break;
  }

  s_mp_2expt(&v, k);       /* v = 2^k   */
  res = mp_mul(&u, &v, c); /* c = u * v */

 CLEANUP:
  mp_clear(&v);
 V:
  mp_clear(&u);
 U:
  mp_clear(&t);

  return res;

} /* end mp_gcd() */

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 98 of file mpi.c.

{
  return s_mp_defprec;

} /* end mp_get_prec() */
mp_err mp_init ( mp_int mp)

Definition at line 125 of file mpi.c.

{
  return mp_init_size(mp, s_mp_defprec);

} /* end mp_init() */

Here is the call graph for this function:

mp_err mp_init_copy ( mp_int mp,
const mp_int from 
)

Definition at line 171 of file mpi.c.

{
  ARGCHK(mp != NULL && from != NULL, MP_BADARG);

  if(mp == from)
    return MP_OKAY;

  if((DIGITS(mp) = s_mp_alloc(ALLOC(from), sizeof(mp_digit))) == NULL)
    return MP_MEM;

  s_mp_copy(DIGITS(from), DIGITS(mp), USED(from));
  USED(mp) = USED(from);
  ALLOC(mp) = ALLOC(from);
  SIGN(mp) = SIGN(from);

  return MP_OKAY;

} /* end mp_init_copy() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_init_size ( mp_int mp,
mp_size  prec 
)

Definition at line 143 of file mpi.c.

{
  ARGCHK(mp != NULL && prec > 0, MP_BADARG);

  prec = MP_ROUNDUP(prec, s_mp_defprec);
  if((DIGITS(mp) = s_mp_alloc(prec, sizeof(mp_digit))) == NULL)
    return MP_MEM;

  SIGN(mp) = ZPOS;
  USED(mp) = 1;
  ALLOC(mp) = prec;

  return MP_OKAY;

} /* end mp_init_size() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_invmod ( const mp_int a,
const mp_int m,
mp_int c 
)

Definition at line 2420 of file mpi.c.

{

  ARGCHK(a && m && c, MP_BADARG);

  if(mp_cmp_z(a) == 0 || mp_cmp_z(m) == 0)
    return MP_RANGE;

  if (mp_isodd(m)) {
    return s_mp_invmod_odd_m(a, m, c);
  }
  if (mp_iseven(a))
    return MP_UNDEF; /* not invertable */

  return s_mp_invmod_even_m(a, m, c);

} /* end mp_invmod() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_invmod_xgcd ( const mp_int a,
const mp_int m,
mp_int c 
)

Definition at line 2245 of file mpi.c.

{
  mp_int  g, x;
  mp_err  res;

  ARGCHK(a && m && c, MP_BADARG);

  if(mp_cmp_z(a) == 0 || mp_cmp_z(m) == 0)
    return MP_RANGE;

  MP_DIGITS(&g) = 0;
  MP_DIGITS(&x) = 0;
  MP_CHECKOK( mp_init(&x) );
  MP_CHECKOK( mp_init(&g) );

  MP_CHECKOK( mp_xgcd(a, m, &g, &x, NULL) );

  if (mp_cmp_d(&g, 1) != MP_EQ) {
    res = MP_UNDEF;
    goto CLEANUP;
  }

  res = mp_mod(&x, m, c);
  SIGN(c) = SIGN(a);

CLEANUP:
  mp_clear(&x);
  mp_clear(&g);

  return res;
}

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 1758 of file mpi.c.

{
  return !mp_isodd(a);

} /* end mp_iseven() */

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 1746 of file mpi.c.

{
  ARGCHK(a != NULL, 0);

  return (int)(DIGIT(a, 0) & 1);

} /* end mp_isodd() */

Here is the caller graph for this function:

mp_err mp_lcm ( mp_int a,
mp_int b,
mp_int c 
)

Definition at line 1880 of file mpi.c.

{
  mp_int  gcd, prod;
  mp_err  res;

  ARGCHK(a != NULL && b != NULL && c != NULL, MP_BADARG);

  /* Set up temporaries */
  if((res = mp_init(&gcd)) != MP_OKAY)
    return res;
  if((res = mp_init(&prod)) != MP_OKAY)
    goto GCD;

  if((res = mp_mul(a, b, &prod)) != MP_OKAY)
    goto CLEANUP;
  if((res = mp_gcd(a, b, &gcd)) != MP_OKAY)
    goto CLEANUP;

  res = mp_div(&prod, &gcd, c, NULL);

 CLEANUP:
  mp_clear(&prod);
 GCD:
  mp_clear(&gcd);

  return res;

} /* end mp_lcm() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_mod ( const mp_int a,
const mp_int m,
mp_int c 
)

Definition at line 1210 of file mpi.c.

{
  mp_err  res;
  int     mag;

  ARGCHK(a != NULL && m != NULL && c != NULL, MP_BADARG);

  if(SIGN(m) == NEG)
    return MP_RANGE;

  /*
     If |a| > m, we need to divide to get the remainder and take the
     absolute value.  

     If |a| < m, we don't need to do any division, just copy and adjust
     the sign (if a is negative).

     If |a| == m, we can simply set the result to zero.

     This order is intended to minimize the average path length of the
     comparison chain on common workloads -- the most frequent cases are
     that |a| != m, so we do those first.
   */
  if((mag = s_mp_cmp(a, m)) > 0) {
    if((res = mp_div(a, m, NULL, c)) != MP_OKAY)
      return res;
    
    if(SIGN(c) == NEG) {
      if((res = mp_add(c, m, c)) != MP_OKAY)
       return res;
    }

  } else if(mag < 0) {
    if((res = mp_copy(a, c)) != MP_OKAY)
      return res;

    if(mp_cmp_z(a) < 0) {
      if((res = mp_add(c, m, c)) != MP_OKAY)
       return res;

    }
    
  } else {
    mp_zero(c);

  }

  return MP_OKAY;

} /* end mp_mod() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_mod_d ( const mp_int a,
mp_digit  d,
mp_digit c 
)

Definition at line 1270 of file mpi.c.

{
  mp_err   res;
  mp_digit rem;

  ARGCHK(a != NULL && c != NULL, MP_BADARG);

  if(s_mp_cmp_d(a, d) > 0) {
    if((res = mp_div_d(a, d, NULL, &rem)) != MP_OKAY)
      return res;

  } else {
    if(SIGN(a) == NEG)
      rem = d - DIGIT(a, 0);
    else
      rem = DIGIT(a, 0);
  }

  if(c)
    *c = rem;

  return MP_OKAY;

} /* end mp_mod_d() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_mul ( const mp_int a,
const mp_int b,
mp_int c 
)

Definition at line 813 of file mpi.c.

{
  mp_digit *pb;
  mp_int   tmp;
  mp_err   res;
  mp_size  ib;
  mp_size  useda, usedb;

  ARGCHK(a != NULL && b != NULL && c != NULL, MP_BADARG);

  if (a == c) {
    if ((res = mp_init_copy(&tmp, a)) != MP_OKAY)
      return res;
    if (a == b) 
      b = &tmp;
    a = &tmp;
  } else if (b == c) {
    if ((res = mp_init_copy(&tmp, b)) != MP_OKAY)
      return res;
    b = &tmp;
  } else {
    MP_DIGITS(&tmp) = 0;
  }

  if (MP_USED(a) < MP_USED(b)) {
    const mp_int *xch = b;  /* switch a and b, to do fewer outer loops */
    b = a;
    a = xch;
  }

  MP_USED(c) = 1; MP_DIGIT(c, 0) = 0;
  if((res = s_mp_pad(c, USED(a) + USED(b))) != MP_OKAY)
    goto CLEANUP;

#ifdef NSS_USE_COMBA
  if ((MP_USED(a) == MP_USED(b)) && IS_POWER_OF_2(MP_USED(b))) {
      if (MP_USED(a) == 4) {
          s_mp_mul_comba_4(a, b, c);
          goto CLEANUP;
      }
      if (MP_USED(a) == 8) {
          s_mp_mul_comba_8(a, b, c);
          goto CLEANUP;
      }
      if (MP_USED(a) == 16) {
          s_mp_mul_comba_16(a, b, c);
          goto CLEANUP;
      }
      if (MP_USED(a) == 32) {
          s_mp_mul_comba_32(a, b, c);
          goto CLEANUP;
      } 
  }
#endif

  pb = MP_DIGITS(b);
  s_mpv_mul_d(MP_DIGITS(a), MP_USED(a), *pb++, MP_DIGITS(c));

  /* Outer loop:  Digits of b */
  useda = MP_USED(a);
  usedb = MP_USED(b);
  for (ib = 1; ib < usedb; ib++) {
    mp_digit b_i    = *pb++;

    /* Inner product:  Digits of a */
    if (b_i)
      s_mpv_mul_d_add(MP_DIGITS(a), useda, b_i, MP_DIGITS(c) + ib);
    else
      MP_DIGIT(c, ib + useda) = b_i;
  }

  s_mp_clamp(c);

  if(SIGN(a) == SIGN(b) || s_mp_cmp_d(c, 0) == MP_EQ)
    SIGN(c) = ZPOS;
  else
    SIGN(c) = NEG;

CLEANUP:
  mp_clear(&tmp);
  return res;
} /* end mp_mul() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_mul_2 ( const mp_int a,
mp_int c 
)

Definition at line 532 of file mpi.c.

{
  mp_err  res;

  ARGCHK(a != NULL && c != NULL, MP_BADARG);

  if((res = mp_copy(a, c)) != MP_OKAY)
    return res;

  return s_mp_mul_2(c);

} /* end mp_mul_2() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_mul_d ( const mp_int a,
mp_digit  d,
mp_int b 
)

Definition at line 508 of file mpi.c.

{
  mp_err  res;

  ARGCHK(a != NULL && b != NULL, MP_BADARG);

  if(d == 0) {
    mp_zero(b);
    return MP_OKAY;
  }

  if((res = mp_copy(a, b)) != MP_OKAY)
    return res;

  res = s_mp_mul_d(b, d);

  return res;

} /* end mp_mul_d() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_mulmod ( const mp_int a,
const mp_int b,
const mp_int m,
mp_int c 
)

Definition at line 1443 of file mpi.c.

{
  mp_err  res;

  ARGCHK(a != NULL && b != NULL && m != NULL && c != NULL, MP_BADARG);

  if((res = mp_mul(a, b, c)) != MP_OKAY)
    return res;
  if((res = mp_mod(c, m, c)) != MP_OKAY)
    return res;

  return MP_OKAY;

}

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_neg ( const mp_int a,
mp_int b 
)

Definition at line 712 of file mpi.c.

{
  mp_err   res;

  ARGCHK(a != NULL && b != NULL, MP_BADARG);

  if((res = mp_copy(a, b)) != MP_OKAY)
    return res;

  if(s_mp_cmp_d(b, 0) == MP_EQ) 
    SIGN(b) = ZPOS;
  else 
    SIGN(b) = (SIGN(b) == NEG) ? ZPOS : NEG;

  return MP_OKAY;

} /* end mp_neg() */

Here is the call graph for this function:

Here is the caller graph for this function:

int mp_radix_size ( mp_int mp,
int  radix 
)

Definition at line 2650 of file mpi.c.

{
  int  bits;

  if(!mp || radix < 2 || radix > MAX_RADIX)
    return 0;

  bits = USED(mp) * DIGIT_BIT - 1;
 
  return s_mp_outlen(bits, radix);

} /* end mp_radix_size() */

Here is the call graph for this function:

Here is the caller graph for this function:

int mp_raw_size ( mp_int mp)

Definition at line 2516 of file mpi.c.

{
  ARGCHK(mp != NULL, 0);

  return (USED(mp) * sizeof(mp_digit)) + 1;

} /* end mp_raw_size() */

Here is the caller graph for this function:

mp_err mp_read_radix ( mp_int mp,
const char *  str,
int  radix 
)

Definition at line 2563 of file mpi.c.

{
  int     ix = 0, val = 0;
  mp_err  res;
  mp_sign sig = ZPOS;

  ARGCHK(mp != NULL && str != NULL && radix >= 2 && radix <= MAX_RADIX, 
        MP_BADARG);

  mp_zero(mp);

  /* Skip leading non-digit characters until a digit or '-' or '+' */
  while(str[ix] && 
       (s_mp_tovalue(str[ix], radix) < 0) && 
       str[ix] != '-' &&
       str[ix] != '+') {
    ++ix;
  }

  if(str[ix] == '-') {
    sig = NEG;
    ++ix;
  } else if(str[ix] == '+') {
    sig = ZPOS; /* this is the default anyway... */
    ++ix;
  }

  while((val = s_mp_tovalue(str[ix], radix)) >= 0) {
    if((res = s_mp_mul_d(mp, radix)) != MP_OKAY)
      return res;
    if((res = s_mp_add_d(mp, val)) != MP_OKAY)
      return res;
    ++ix;
  }

  if(s_mp_cmp_d(mp, 0) == MP_EQ)
    SIGN(mp) = ZPOS;
  else
    SIGN(mp) = sig;

  return MP_OKAY;

} /* end mp_read_radix() */

Here is the call graph for this function:

mp_err mp_read_raw ( mp_int mp,
char *  str,
int  len 
)

Definition at line 2484 of file mpi.c.

{
  int            ix;
  mp_err         res;
  unsigned char *ustr = (unsigned char *)str;

  ARGCHK(mp != NULL && str != NULL && len > 0, MP_BADARG);

  mp_zero(mp);

  /* Get sign from first byte */
  if(ustr[0])
    SIGN(mp) = NEG;
  else
    SIGN(mp) = ZPOS;

  /* Read the rest of the digits */
  for(ix = 1; ix < len; ix++) {
    if((res = mp_mul_d(mp, 256, mp)) != MP_OKAY)
      return res;
    if((res = mp_add_d(mp, ustr[ix], mp)) != MP_OKAY)
      return res;
  }

  return MP_OKAY;

} /* end mp_read_raw() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_read_unsigned_octets ( mp_int mp,
const unsigned char *  str,
mp_size  len 
)

Definition at line 4665 of file mpi.c.

{
  int            count;
  mp_err         res;
  mp_digit       d;

  ARGCHK(mp != NULL && str != NULL && len > 0, MP_BADARG);

  mp_zero(mp);

  count = len % sizeof(mp_digit);
  if (count) {
    for (d = 0; count-- > 0; --len) {
      d = (d << 8) | *str++;
    }
    MP_DIGIT(mp, 0) = d;
  }

  /* Read the rest of the digits */
  for(; len > 0; len -= sizeof(mp_digit)) {
    for (d = 0, count = sizeof(mp_digit); count > 0; --count) {
      d = (d << 8) | *str++;
    }
    if (MP_EQ == mp_cmp_z(mp)) {
      if (!d)
       continue;
    } else {
      if((res = s_mp_lshd(mp, 1)) != MP_OKAY)
       return res;
    }
    MP_DIGIT(mp, 0) = d;
  }
  return MP_OKAY;
} /* end mp_read_unsigned_octets() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_read_variable_radix ( mp_int a,
const char *  str,
int  default_radix 
)

Definition at line 2607 of file mpi.c.

{
  int     radix = default_radix;
  int     cx;
  mp_sign sig   = ZPOS;
  mp_err  res;

  /* Skip leading non-digit characters until a digit or '-' or '+' */
  while ((cx = *str) != 0 && 
       (s_mp_tovalue(cx, radix) < 0) && 
       cx != '-' &&
       cx != '+') {
    ++str;
  }

  if (cx == '-') {
    sig = NEG;
    ++str;
  } else if (cx == '+') {
    sig = ZPOS; /* this is the default anyway... */
    ++str;
  }

  if (str[0] == '0') {
    if ((str[1] | 0x20) == 'x') {
      radix = 16;
      str += 2;
    } else {
      radix = 8;
      str++;
    }
  }
  res = mp_read_radix(a, str, radix);
  if (res == MP_OKAY) {
    MP_SIGN(a) = (s_mp_cmp_d(a, 0) == MP_EQ) ? ZPOS : sig;
  }
  return res;
}

Here is the call graph for this function:

Here is the caller graph for this function:

void mp_set ( mp_int mp,
mp_digit  d 
)

Definition at line 330 of file mpi.c.

{
  if(mp == NULL)
    return;

  mp_zero(mp);
  DIGIT(mp, 0) = d;

} /* end mp_set() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_set_int ( mp_int mp,
long  z 
)

Definition at line 344 of file mpi.c.

{
  int            ix;
  unsigned long  v = labs(z);
  mp_err         res;

  ARGCHK(mp != NULL, MP_BADARG);

  mp_zero(mp);
  if(z == 0)
    return MP_OKAY;  /* shortcut for zero */

  if (sizeof v <= sizeof(mp_digit)) {
    DIGIT(mp,0) = v;
  } else {
    for (ix = sizeof(long) - 1; ix >= 0; ix--) {
      if ((res = s_mp_mul_d(mp, (UCHAR_MAX + 1))) != MP_OKAY)
       return res;

      res = s_mp_add_d(mp, (mp_digit)((v >> (ix * CHAR_BIT)) & UCHAR_MAX));
      if (res != MP_OKAY)
       return res;
    }
  }
  if(z < 0)
    SIGN(mp) = NEG;

  return MP_OKAY;

} /* end mp_set_int() */

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 104 of file mpi.c.

{
  if(prec == 0)
    s_mp_defprec = MP_DEFPREC;
  else
    s_mp_defprec = prec;

} /* end mp_set_prec() */
mp_err mp_set_ulong ( mp_int mp,
unsigned long  z 
)

Definition at line 379 of file mpi.c.

{
  int            ix;
  mp_err         res;

  ARGCHK(mp != NULL, MP_BADARG);

  mp_zero(mp);
  if(z == 0)
    return MP_OKAY;  /* shortcut for zero */

  if (sizeof z <= sizeof(mp_digit)) {
    DIGIT(mp,0) = z;
  } else {
    for (ix = sizeof(long) - 1; ix >= 0; ix--) {
      if ((res = s_mp_mul_d(mp, (UCHAR_MAX + 1))) != MP_OKAY)
       return res;

      res = s_mp_add_d(mp, (mp_digit)((z >> (ix * CHAR_BIT)) & UCHAR_MAX));
      if (res != MP_OKAY)
       return res;
    }
  }
  return MP_OKAY;
} /* end mp_set_ulong() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_sqr ( const mp_int a,
mp_int b 
)

Definition at line 910 of file mpi.c.

{
  mp_digit *pa;
  mp_digit d;
  mp_err   res;
  mp_size  ix;
  mp_int   tmp;
  int      count;

  ARGCHK(a != NULL && sqr != NULL, MP_BADARG);

  if (a == sqr) {
    if((res = mp_init_copy(&tmp, a)) != MP_OKAY)
      return res;
    a = &tmp;
  } else {
    DIGITS(&tmp) = 0;
    res = MP_OKAY;
  }

  ix = 2 * MP_USED(a);
  if (ix > MP_ALLOC(sqr)) {
    MP_USED(sqr) = 1; 
    MP_CHECKOK( s_mp_grow(sqr, ix) );
  } 
  MP_USED(sqr) = ix;
  MP_DIGIT(sqr, 0) = 0;

#ifdef NSS_USE_COMBA
  if (IS_POWER_OF_2(MP_USED(a))) {
      if (MP_USED(a) == 4) {
          s_mp_sqr_comba_4(a, sqr);
          goto CLEANUP;
      }
      if (MP_USED(a) == 8) {
          s_mp_sqr_comba_8(a, sqr);
          goto CLEANUP;
      }
      if (MP_USED(a) == 16) {
          s_mp_sqr_comba_16(a, sqr);
          goto CLEANUP;
      }
      if (MP_USED(a) == 32) {
          s_mp_sqr_comba_32(a, sqr);
          goto CLEANUP;
      } 
  }
#endif

  pa = MP_DIGITS(a);
  count = MP_USED(a) - 1;
  if (count > 0) {
    d = *pa++;
    s_mpv_mul_d(pa, count, d, MP_DIGITS(sqr) + 1);
    for (ix = 3; --count > 0; ix += 2) {
      d = *pa++;
      s_mpv_mul_d_add(pa, count, d, MP_DIGITS(sqr) + ix);
    } /* for(ix ...) */
    MP_DIGIT(sqr, MP_USED(sqr)-1) = 0; /* above loop stopped short of this. */

    /* now sqr *= 2 */
    s_mp_mul_2(sqr);
  } else {
    MP_DIGIT(sqr, 1) = 0;
  }

  /* now add the squares of the digits of a to sqr. */
  s_mpv_sqr_add_prop(MP_DIGITS(a), MP_USED(a), MP_DIGITS(sqr));

  SIGN(sqr) = ZPOS;
  s_mp_clamp(sqr);

CLEANUP:
  mp_clear(&tmp);
  return res;

} /* end mp_sqr() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_sqrmod ( const mp_int a,
const mp_int m,
mp_int c 
)

Definition at line 1463 of file mpi.c.

{
  mp_err  res;

  ARGCHK(a != NULL && m != NULL && c != NULL, MP_BADARG);

  if((res = mp_sqr(a, c)) != MP_OKAY)
    return res;
  if((res = mp_mod(c, m, c)) != MP_OKAY)
    return res;

  return MP_OKAY;

} /* end mp_sqrmod() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_sqrt ( const mp_int a,
mp_int b 
)

Definition at line 1312 of file mpi.c.

{
  mp_int   x, t;
  mp_err   res;
  mp_size  used;

  ARGCHK(a != NULL && b != NULL, MP_BADARG);

  /* Cannot take square root of a negative value */
  if(SIGN(a) == NEG)
    return MP_RANGE;

  /* Special cases for zero and one, trivial     */
  if(mp_cmp_d(a, 1) <= 0)
    return mp_copy(a, b);
    
  /* Initialize the temporaries we'll use below  */
  if((res = mp_init_size(&t, USED(a))) != MP_OKAY)
    return res;

  /* Compute an initial guess for the iteration as a itself */
  if((res = mp_init_copy(&x, a)) != MP_OKAY)
    goto X;

  used = MP_USED(&x);
  if (used > 1) {
    s_mp_rshd(&x, used / 2);
  }

  for(;;) {
    /* t = (x * x) - a */
    mp_copy(&x, &t);      /* can't fail, t is big enough for original x */
    if((res = mp_sqr(&t, &t)) != MP_OKAY ||
       (res = mp_sub(&t, a, &t)) != MP_OKAY)
      goto CLEANUP;

    /* t = t / 2x       */
    s_mp_mul_2(&x);
    if((res = mp_div(&t, &x, &t, NULL)) != MP_OKAY)
      goto CLEANUP;
    s_mp_div_2(&x);

    /* Terminate the loop, if the quotient is zero */
    if(mp_cmp_z(&t) == MP_EQ)
      break;

    /* x = x - t       */
    if((res = mp_sub(&x, &t, &x)) != MP_OKAY)
      goto CLEANUP;

  }

  /* Copy result to output parameter */
  mp_sub_d(&x, 1, &x);
  s_mp_exch(&x, b);

 CLEANUP:
  mp_clear(&x);
 X:
  mp_clear(&t); 

  return res;

} /* end mp_sqrt() */

Here is the call graph for this function:

Here is the caller graph for this function:

const char* mp_strerror ( mp_err  ec)

Definition at line 2752 of file mpi.c.

{
  int   aec = (ec < 0) ? -ec : ec;

  /* Code values are negative, so the senses of these comparisons
     are accurate */
  if(ec < MP_LAST_CODE || ec > MP_OKAY) {
    return mp_err_string[0];  /* unknown error code */
  } else {
    return mp_err_string[aec + 1];
  }

} /* end mp_strerror() */

Here is the caller graph for this function:

mp_err mp_sub ( const mp_int a,
const mp_int b,
mp_int c 
)

Definition at line 772 of file mpi.c.

{
  mp_err  res;
  int     magDiff;

  ARGCHK(a != NULL && b != NULL && c != NULL, MP_BADARG);

  if (a == b) {
    mp_zero(c);
    return MP_OKAY;
  }

  if (MP_SIGN(a) != MP_SIGN(b)) {
    MP_CHECKOK( s_mp_add_3arg(a, b, c) );
  } else if (!(magDiff = s_mp_cmp(a, b))) {
    mp_zero(c);
    res = MP_OKAY;
  } else if (magDiff > 0) {
    MP_CHECKOK( s_mp_sub_3arg(a, b, c) );
  } else {
    MP_CHECKOK( s_mp_sub_3arg(b, a, c) );
    MP_SIGN(c) = !MP_SIGN(a);
  }

  if (s_mp_cmp_d(c, 0) == MP_EQ)
    MP_SIGN(c) = MP_ZPOS;

CLEANUP:
  return res;

} /* end mp_sub() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_sub_d ( const mp_int a,
mp_digit  d,
mp_int b 
)

Definition at line 463 of file mpi.c.

{
  mp_int   tmp;
  mp_err   res;

  ARGCHK(a != NULL && b != NULL, MP_BADARG);

  if((res = mp_init_copy(&tmp, a)) != MP_OKAY)
    return res;

  if(SIGN(&tmp) == NEG) {
    if((res = s_mp_add_d(&tmp, d)) != MP_OKAY)
      goto CLEANUP;
  } else if(s_mp_cmp_d(&tmp, d) >= 0) {
    if((res = s_mp_sub_d(&tmp, d)) != MP_OKAY)
      goto CLEANUP;
  } else {
    mp_neg(&tmp, &tmp);

    DIGIT(&tmp, 0) = d - DIGIT(&tmp, 0);
    SIGN(&tmp) = NEG;
  }

  if(s_mp_cmp_d(&tmp, 0) == 0)
    SIGN(&tmp) = ZPOS;

  s_mp_exch(&tmp, b);

CLEANUP:
  mp_clear(&tmp);
  return res;

} /* end mp_sub_d() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_submod ( const mp_int a,
const mp_int b,
const mp_int m,
mp_int c 
)

Definition at line 1418 of file mpi.c.

{
  mp_err  res;

  ARGCHK(a != NULL && b != NULL && m != NULL && c != NULL, MP_BADARG);

  if((res = mp_sub(a, b, c)) != MP_OKAY)
    return res;
  if((res = mp_mod(c, m, c)) != MP_OKAY)
    return res;

  return MP_OKAY;

}

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_to_fixlen_octets ( const mp_int mp,
unsigned char *  str,
mp_size  len 
)

Definition at line 4811 of file mpi.c.

{
  int  ix, pos = 0;
  int  bytes;

  ARGCHK(mp != NULL && str != NULL && !SIGN(mp), MP_BADARG);

  bytes = mp_unsigned_octet_size(mp);
  ARGCHK(bytes <= length, MP_BADARG);

  /* place any needed leading zeros */
  for (;length > bytes; --length) {
       *str++ = 0;
  }

  /* Iterate over each digit... */
  for(ix = USED(mp) - 1; ix >= 0; ix--) {
    mp_digit  d = DIGIT(mp, ix);
    int       jx;

    /* Unpack digit bytes, high order first */
    for(jx = sizeof(mp_digit) - 1; jx >= 0; jx--) {
      unsigned char x = (unsigned char)(d >> (jx * CHAR_BIT));
      if (!pos && !x)       /* suppress leading zeros */
       continue;
      str[pos++] = x;
    }
  }
  if (!pos)
    str[pos++] = 0;
  return MP_OKAY;
} /* end mp_to_fixlen_octets() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_to_signed_octets ( const mp_int mp,
unsigned char *  str,
mp_size  maxlen 
)

Definition at line 4771 of file mpi.c.

{
  int  ix, pos = 0;
  int  bytes;

  ARGCHK(mp != NULL && str != NULL && !SIGN(mp), MP_BADARG);

  bytes = mp_unsigned_octet_size(mp);
  ARGCHK(bytes <= maxlen, MP_BADARG);

  /* Iterate over each digit... */
  for(ix = USED(mp) - 1; ix >= 0; ix--) {
    mp_digit  d = DIGIT(mp, ix);
    int       jx;

    /* Unpack digit bytes, high order first */
    for(jx = sizeof(mp_digit) - 1; jx >= 0; jx--) {
      unsigned char x = (unsigned char)(d >> (jx * CHAR_BIT));
      if (!pos) {
       if (!x)              /* suppress leading zeros */
         continue;
       if (x & 0x80) { /* add one leading zero to make output positive.  */
         ARGCHK(bytes + 1 <= maxlen, MP_BADARG);
         if (bytes + 1 > maxlen)
           return MP_BADARG;
         str[pos++] = 0;
       }
      }
      str[pos++] = x;
    }
  }
  if (!pos)
    str[pos++] = 0;
  return pos;
} /* end mp_to_signed_octets() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_to_unsigned_octets ( const mp_int mp,
unsigned char *  str,
mp_size  maxlen 
)

Definition at line 4739 of file mpi.c.

{
  int  ix, pos = 0;
  int  bytes;

  ARGCHK(mp != NULL && str != NULL && !SIGN(mp), MP_BADARG);

  bytes = mp_unsigned_octet_size(mp);
  ARGCHK(bytes <= maxlen, MP_BADARG);

  /* Iterate over each digit... */
  for(ix = USED(mp) - 1; ix >= 0; ix--) {
    mp_digit  d = DIGIT(mp, ix);
    int       jx;

    /* Unpack digit bytes, high order first */
    for(jx = sizeof(mp_digit) - 1; jx >= 0; jx--) {
      unsigned char x = (unsigned char)(d >> (jx * CHAR_BIT));
      if (!pos && !x)       /* suppress leading zeros */
       continue;
      str[pos++] = x;
    }
  }
  if (!pos)
    str[pos++] = 0;
  return pos;
} /* end mp_to_unsigned_octets() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_toradix ( mp_int mp,
char *  str,
int  radix 
)

Definition at line 2667 of file mpi.c.

{
  int  ix, pos = 0;

  ARGCHK(mp != NULL && str != NULL, MP_BADARG);
  ARGCHK(radix > 1 && radix <= MAX_RADIX, MP_RANGE);

  if(mp_cmp_z(mp) == MP_EQ) {
    str[0] = '0';
    str[1] = '\0';
  } else {
    mp_err   res;
    mp_int   tmp;
    mp_sign  sgn;
    mp_digit rem, rdx = (mp_digit)radix;
    char     ch;

    if((res = mp_init_copy(&tmp, mp)) != MP_OKAY)
      return res;

    /* Save sign for later, and take absolute value */
    sgn = SIGN(&tmp); SIGN(&tmp) = ZPOS;

    /* Generate output digits in reverse order      */
    while(mp_cmp_z(&tmp) != 0) {
      if((res = mp_div_d(&tmp, rdx, &tmp, &rem)) != MP_OKAY) {
       mp_clear(&tmp);
       return res;
      }

      /* Generate digits, use capital letters */
      ch = s_mp_todigit(rem, radix, 0);

      str[pos++] = ch;
    }

    /* Add - sign if original value was negative */
    if(sgn == NEG)
      str[pos++] = '-';

    /* Add trailing NUL to end the string        */
    str[pos--] = '\0';

    /* Reverse the digits and sign indicator     */
    ix = 0;
    while(ix < pos) {
      char tmp = str[ix];

      str[ix] = str[pos];
      str[pos] = tmp;
      ++ix;
      --pos;
    }
    
    mp_clear(&tmp);
  }

  return MP_OKAY;

} /* end mp_toradix() */

Here is the call graph for this function:

Here is the caller graph for this function:

mp_err mp_toraw ( mp_int mp,
char *  str 
)

Definition at line 2528 of file mpi.c.

{
  int  ix, jx, pos = 1;

  ARGCHK(mp != NULL && str != NULL, MP_BADARG);

  str[0] = (char)SIGN(mp);

  /* Iterate over each digit... */
  for(ix = USED(mp) - 1; ix >= 0; ix--) {
    mp_digit  d = DIGIT(mp, ix);

    /* Unpack digit bytes, high order first */
    for(jx = sizeof(mp_digit) - 1; jx >= 0; jx--) {
      str[pos++] = (char)(d >> (jx * CHAR_BIT));
    }
  }

  return MP_OKAY;

} /* end mp_toraw() */

Here is the caller graph for this function:

int mp_tovalue ( char  ch,
int  r 
)

Definition at line 2732 of file mpi.c.

{
  return s_mp_tovalue(ch, r);

} /* end mp_tovalue() */

Here is the call graph for this function:

Definition at line 2029 of file mpi.c.

{
  mp_digit d;
  mp_size  n = 0;
  int      ix;

  if (!mp || !MP_DIGITS(mp) || !mp_cmp_z(mp))
    return n;

  for (ix = 0; !(d = MP_DIGIT(mp,ix)) && (ix < MP_USED(mp)); ++ix)
    n += MP_DIGIT_BIT;
  if (!d)
    return 0; /* shouldn't happen, but ... */
#if !defined(MP_USE_UINT_DIGIT)
  if (!(d & 0xffffffffU)) {
    d >>= 32;
    n  += 32;
  }
#endif
  if (!(d & 0xffffU)) {
    d >>= 16;
    n  += 16;
  }
  if (!(d & 0xffU)) {
    d >>= 8;
    n  += 8;
  }
  if (!(d & 0xfU)) {
    d >>= 4;
    n  += 4;
  }
  if (!(d & 0x3U)) {
    d >>= 2;
    n  += 2;
  }
  if (!(d & 0x1U)) {
    d >>= 1;
    n  += 1;
  }
#if MP_ARGCHK == 2
  assert(0 != (d & 1));
#endif
  return n;
}

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 4703 of file mpi.c.

{
  int  bytes;
  int  ix;
  mp_digit  d = 0;

  ARGCHK(mp != NULL, MP_BADARG);
  ARGCHK(MP_ZPOS == SIGN(mp), MP_BADARG);

  bytes = (USED(mp) * sizeof(mp_digit));

  /* subtract leading zeros. */
  /* Iterate over each digit... */
  for(ix = USED(mp) - 1; ix >= 0; ix--) {
    d = DIGIT(mp, ix);
    if (d) 
       break;
    bytes -= sizeof(d);
  }
  if (!bytes)
    return 1;

  /* Have MSD, check digit bytes, high order first */
  for(ix = sizeof(mp_digit) - 1; ix >= 0; ix--) {
    unsigned char x = (unsigned char)(d >> (ix * CHAR_BIT));
    if (x) 
       break;
    --bytes;
  }
  return bytes;
} /* end mp_unsigned_octet_size() */

Here is the caller graph for this function:

mp_err mp_xgcd ( const mp_int a,
const mp_int b,
mp_int g,
mp_int x,
mp_int y 
)

Definition at line 1922 of file mpi.c.

{
  mp_int   gx, xc, yc, u, v, A, B, C, D;
  mp_int  *clean[9];
  mp_err   res;
  int      last = -1;

  if(mp_cmp_z(b) == 0)
    return MP_RANGE;

  /* Initialize all these variables we need */
  MP_CHECKOK( mp_init(&u) );
  clean[++last] = &u;
  MP_CHECKOK( mp_init(&v) );
  clean[++last] = &v;
  MP_CHECKOK( mp_init(&gx) );
  clean[++last] = &gx;
  MP_CHECKOK( mp_init(&A) );
  clean[++last] = &A;
  MP_CHECKOK( mp_init(&B) );
  clean[++last] = &B;
  MP_CHECKOK( mp_init(&C) );
  clean[++last] = &C;
  MP_CHECKOK( mp_init(&D) );
  clean[++last] = &D;
  MP_CHECKOK( mp_init_copy(&xc, a) );
  clean[++last] = &xc;
  mp_abs(&xc, &xc);
  MP_CHECKOK( mp_init_copy(&yc, b) );
  clean[++last] = &yc;
  mp_abs(&yc, &yc);

  mp_set(&gx, 1);

  /* Divide by two until at least one of them is odd */
  while(mp_iseven(&xc) && mp_iseven(&yc)) {
    mp_size nx = mp_trailing_zeros(&xc);
    mp_size ny = mp_trailing_zeros(&yc);
    mp_size n  = MP_MIN(nx, ny);
    s_mp_div_2d(&xc,n);
    s_mp_div_2d(&yc,n);
    MP_CHECKOK( s_mp_mul_2d(&gx,n) );
  }

  mp_copy(&xc, &u);
  mp_copy(&yc, &v);
  mp_set(&A, 1); mp_set(&D, 1);

  /* Loop through binary GCD algorithm */
  do {
    while(mp_iseven(&u)) {
      s_mp_div_2(&u);

      if(mp_iseven(&A) && mp_iseven(&B)) {
       s_mp_div_2(&A); s_mp_div_2(&B);
      } else {
       MP_CHECKOK( mp_add(&A, &yc, &A) );
       s_mp_div_2(&A);
       MP_CHECKOK( mp_sub(&B, &xc, &B) );
       s_mp_div_2(&B);
      }
    }

    while(mp_iseven(&v)) {
      s_mp_div_2(&v);

      if(mp_iseven(&C) && mp_iseven(&D)) {
       s_mp_div_2(&C); s_mp_div_2(&D);
      } else {
       MP_CHECKOK( mp_add(&C, &yc, &C) );
       s_mp_div_2(&C);
       MP_CHECKOK( mp_sub(&D, &xc, &D) );
       s_mp_div_2(&D);
      }
    }

    if(mp_cmp(&u, &v) >= 0) {
      MP_CHECKOK( mp_sub(&u, &v, &u) );
      MP_CHECKOK( mp_sub(&A, &C, &A) );
      MP_CHECKOK( mp_sub(&B, &D, &B) );
    } else {
      MP_CHECKOK( mp_sub(&v, &u, &v) );
      MP_CHECKOK( mp_sub(&C, &A, &C) );
      MP_CHECKOK( mp_sub(&D, &B, &D) );
    }
  } while (mp_cmp_z(&u) != 0);

  /* copy results to output */
  if(x)
    MP_CHECKOK( mp_copy(&C, x) );

  if(y)
    MP_CHECKOK( mp_copy(&D, y) );
      
  if(g)
    MP_CHECKOK( mp_mul(&gx, &v, g) );

 CLEANUP:
  while(last >= 0)
    mp_clear(clean[last--]);

  return res;

} /* end mp_xgcd() */

Here is the call graph for this function:

Here is the caller graph for this function:

void mp_zero ( mp_int mp)

Definition at line 315 of file mpi.c.

{
  if(mp == NULL)
    return;

  s_mp_setz(DIGITS(mp), ALLOC(mp));
  USED(mp) = 1;
  SIGN(mp) = ZPOS;

} /* end mp_zero() */

Here is the call graph for this function:

Here is the caller graph for this function: