Esempio n. 1
0
void
mpz_tdiv_q (mpz_ptr quot, mpz_srcptr num, mpz_srcptr den)
{
  mp_size_t ql;
  mp_size_t ns, ds, nl, dl;
  mp_ptr np, dp, qp;
  TMP_DECL;

  ns = SIZ (num);
  ds = SIZ (den);
  nl = ABS (ns);
  dl = ABS (ds);
  ql = nl - dl + 1;

  if (dl == 0)
    DIVIDE_BY_ZERO;

  if (ql <= 0)
    {
      SIZ (quot) = 0;
      return;
    }

  MPZ_REALLOC (quot, ql);

  TMP_MARK;
  qp = PTR (quot);
  np = PTR (num);
  dp = PTR (den);

  /* Copy denominator to temporary space if it overlaps with the quotient.  */
  if (dp == qp)
    {
      mp_ptr tp;
      tp = TMP_ALLOC_LIMBS (dl);
      MPN_COPY (tp, dp, dl);
      dp = tp;
    }
  /* Copy numerator to temporary space if it overlaps with the quotient.  */
  if (np == qp)
    {
      mp_ptr tp;
      tp = TMP_ALLOC_LIMBS (nl + 1);
      MPN_COPY (tp, np, nl);
      /* Overlap dividend and scratch.  */
      mpn_div_q (qp, tp, nl, dp, dl, tp);
    }
  else
    {
      mp_ptr tp;
      tp = TMP_ALLOC_LIMBS (nl + 1);
      mpn_div_q (qp, np, nl, dp, dl, tp);
    }

  ql -=  qp[ql - 1] == 0;

  SIZ (quot) = (ns ^ ds) >= 0 ? ql : -ql;
  TMP_FREE;
}
Esempio n. 2
0
int
mpz_root (mpz_ptr root, mpz_srcptr u, mpir_ui nth)
{
  mp_ptr rootp, up;
  mp_size_t us, un, rootn, remn;
  TMP_DECL;

  us = SIZ(u);

  /* even roots of negatives provoke an exception */
  if (us < 0 && (nth & 1) == 0)
    SQRT_OF_NEGATIVE;

  /* root extraction interpreted as c^(1/nth) means a zeroth root should
     provoke a divide by zero, do this even if c==0 */
  if (nth == 0)
    DIVIDE_BY_ZERO;

  if (us == 0)
    {
      if (root != NULL)
	SIZ(root) = 0;
      return 1;			/* exact result */
    }

  un = ABS (us);
  rootn = (un - 1) / nth + 1;

  TMP_MARK;

  /* FIXME: Perhaps disallow root == NULL */
  if (root != NULL && u != root)
    rootp = MPZ_REALLOC (root, rootn);
  else
    rootp = TMP_ALLOC_LIMBS (rootn);

  up = PTR(u);

  if (nth == 1)
    {
      MPN_COPY (rootp, up, un);
      remn = 0;
    }
  else
    {
      remn = mpn_rootrem (rootp, NULL, up, un, (mp_limb_t) nth);
    }

  if (root != NULL)
    {
      SIZ(root) = us >= 0 ? rootn : -rootn;
      if (u == root)
	MPN_COPY (up, rootp, rootn);
    }

  TMP_FREE;
  return remn == 0;
}
Esempio n. 3
0
static void
matrix_copy (struct matrix *R, const struct matrix *M)
{
  R->n = M->n;
  MPN_COPY (R->e00, M->e00, M->n);
  MPN_COPY (R->e01, M->e01, M->n);
  MPN_COPY (R->e10, M->e10, M->n);
  MPN_COPY (R->e11, M->e11, M->n);
}
Esempio n. 4
0
File: t-mul.c Progetto: HRF92/mpir
static void
ref_mpn_mul (mp_ptr wp, mp_srcptr up, mp_size_t un, mp_srcptr vp, mp_size_t vn)
{
  mp_ptr tp;
  mp_size_t tn;
  mp_limb_t cy;

  if (vn < TOOM3_THRESHOLD)
    {
      /* In the mpn_mul_basecase and mpn_kara_mul_n range, use our own
	 mul_basecase.  */
      if (vn != 0)
	mul_basecase (wp, up, un, vp, vn);
      else
	MPN_ZERO (wp, un);
      return;
    }

  if (vn < FFT_THRESHOLD)
    {
      /* In the mpn_toom3_mul_n and mpn_toom4_mul_n range, use mpn_kara_mul_n.  */
      tn = 2 * vn + MPN_KARA_MUL_N_TSIZE (vn);
      tp = __GMP_ALLOCATE_FUNC_LIMBS (tn);
      mpn_kara_mul_n (tp, up, vp, vn, tp + 2 * vn);
    }
  else
    {
      /* Finally, for the largest operands, use mpn_toom3_mul_n.  */
      /* The "- 63 + 255" tweaks the allocation to allow for huge operands.
	 See the definition of this macro in gmp-impl.h to understand this.  */
      tn = 2 * vn + MPN_TOOM3_MUL_N_TSIZE (vn) - 63 + 255;
      tp = __GMP_ALLOCATE_FUNC_LIMBS (tn);
      mpn_toom3_mul_n (tp, up, vp, vn, tp + 2 * vn);
    }

  if (un != vn)
    {
      if (un - vn < vn)
	ref_mpn_mul (wp + vn, vp, vn, up + vn, un - vn);
      else
	ref_mpn_mul (wp + vn, up + vn, un - vn, vp, vn);

      MPN_COPY (wp, tp, vn);
      cy = mpn_add_n (wp + vn, wp + vn, tp + vn, vn);
      mpn_incr_u (wp + 2 * vn, cy);
    }
  else
    {
      MPN_COPY (wp, tp, 2 * vn);
    }

  __GMP_FREE_FUNC_LIMBS (tp, tn);
}
Esempio n. 5
0
void
mpf_sqrt (mpf_ptr r, mpf_srcptr u)
{
  mp_size_t usize;
  mp_ptr up, tp;
  mp_size_t prec, tsize;
  mp_exp_t uexp, expodd;
  TMP_DECL;

  usize = u->_mp_size;
  if (usize <= 0)
    {
      if (usize < 0)
        SQRT_OF_NEGATIVE;
      r->_mp_size = 0;
      r->_mp_exp = 0;
      return;
    }

  TMP_MARK;

  uexp = u->_mp_exp;
  prec = r->_mp_prec;
  up = u->_mp_d;

  expodd = (uexp & 1);
  tsize = 2 * prec - expodd;
  r->_mp_size = prec;
  r->_mp_exp = (uexp + expodd) / 2;    /* ceil(uexp/2) */

  /* root size is ceil(tsize/2), this will be our desired "prec" limbs */
  ASSERT ((tsize + 1) / 2 == prec);

  tp = (mp_ptr) TMP_ALLOC (tsize * BYTES_PER_MP_LIMB);

  if (usize > tsize)
    {
      up += usize - tsize;
      usize = tsize;
      MPN_COPY (tp, up, tsize);
    }
  else
    {
      MPN_ZERO (tp, tsize - usize);
      MPN_COPY (tp + (tsize - usize), up, usize);
    }

  mpn_sqrtrem (r->_mp_d, NULL, tp, tsize);

  TMP_FREE;
}
Esempio n. 6
0
/* Compute t = a mod m, a is defined by (ap,an), m is defined by (mp,mn), and
   t is defined by (tp,mn).  */
static void
reduce (mp_ptr tp, mp_srcptr ap, mp_size_t an, mp_srcptr mp, mp_size_t mn, gmp_pi1_t *dinv)
{
  mp_ptr rp, scratch;
  TMP_DECL;
  TMP_MARK;

  rp = TMP_ALLOC_LIMBS (an);
  scratch = TMP_ALLOC_LIMBS (an - mn + 1);
  MPN_COPY (rp, ap, an);
  mod (rp, an, mp, mn, dinv, scratch);
  MPN_COPY (tp, rp, mn);

  TMP_FREE;
}
Esempio n. 7
0
void
mpi_set_secure( MPI a )
{
    mpi_ptr_t ap, bp;

    if( (a->flags & 1) )
	return;
    a->flags |= 1;
    ap = a->d;
    if( !a->nlimbs ) {
	assert(!ap);
	return;
    }
#ifdef M_DEBUG
    bp = mpi_debug_alloc_limb_space( a->nlimbs, 1, "set_secure" );
#else
    bp = mpi_alloc_limb_space( a->nlimbs, 1 );
#endif
    MPN_COPY( bp, ap, a->nlimbs );
    a->d = bp;
#ifdef M_DEBUG
    mpi_debug_free_limb_space(ap, "set_secure");
#else
    mpi_free_gpg_limb_space(ap);
#endif
}
Esempio n. 8
0
File: sqrt.c Progetto: mahdiz/mpclib
void
mpz_sqrt (mpz_ptr root, mpz_srcptr op)
{
  mp_size_t op_size, root_size;
  mp_ptr root_ptr, op_ptr;
  mp_ptr free_me = NULL;
  mp_size_t free_me_size;
  TMP_DECL (marker);

  TMP_MARK (marker);
  op_size = op->_mp_size;
  if (op_size <= 0)
    {
      if (op_size < 0)
        SQRT_OF_NEGATIVE;
      SIZ(root) = 0;
      return;
    }

  /* The size of the root is accurate after this simple calculation.  */
  root_size = (op_size + 1) / 2;

  root_ptr = root->_mp_d;
  op_ptr = op->_mp_d;

  if (root->_mp_alloc < root_size)
    {
      if (root_ptr == op_ptr)
	{
	  free_me = root_ptr;
	  free_me_size = root->_mp_alloc;
	}
      else
	(*__gmp_free_func) (root_ptr, root->_mp_alloc * BYTES_PER_MP_LIMB);

      root->_mp_alloc = root_size;
      root_ptr = (mp_ptr) (*__gmp_allocate_func) (root_size * BYTES_PER_MP_LIMB);
      root->_mp_d = root_ptr;
    }
  else
    {
      /* Make OP not overlap with ROOT.  */
      if (root_ptr == op_ptr)
	{
	  /* ROOT and OP are identical.  Allocate temporary space for OP.  */
	  op_ptr = (mp_ptr) TMP_ALLOC (op_size * BYTES_PER_MP_LIMB);
	  /* Copy to the temporary space.  Hack: Avoid temporary variable
	     by using ROOT_PTR.  */
	  MPN_COPY (op_ptr, root_ptr, op_size);
	}
    }

  mpn_sqrtrem (root_ptr, NULL, op_ptr, op_size);

  root->_mp_size = root_size;

  if (free_me != NULL)
    (*__gmp_free_func) (free_me, free_me_size * BYTES_PER_MP_LIMB);
  TMP_FREE (marker);
}
Esempio n. 9
0
void
mpf_init_set (mpf_ptr r, mpf_srcptr s)
{
    mp_ptr rp, sp;
    mp_size_t ssize, size;
    mp_size_t prec;

    prec = __gmp_default_fp_limb_precision;
    r->_mp_d = __GMP_ALLOCATE_FUNC_LIMBS (prec + 1);
    r->_mp_prec = prec;

    prec++;		/* lie not to lose precision in assignment */
    ssize = s->_mp_size;
    size = ABS (ssize);

    rp = r->_mp_d;
    sp = s->_mp_d;

    if (size > prec)
    {
        sp += size - prec;
        size = prec;
    }

    r->_mp_exp = s->_mp_exp;
    r->_mp_size = ssize >= 0 ? size : -size;

    MPN_COPY (rp, sp, size);
}
Esempio n. 10
0
int
test_invert (mp_ptr xp, mp_srcptr ap, mp_size_t n)
{
  int res = 1;
  mp_size_t i;
  mp_ptr tp, up;
  mp_limb_t cy;
  TMP_DECL;

  TMP_MARK;
  tp = TMP_ALLOC_LIMBS (2 * n);
  up = TMP_ALLOC_LIMBS (2 * n);

  /* first check X*A < B^(2*n) */
  mpn_mul_n (tp, xp, ap, n);
  cy = mpn_add_n (tp + n, tp + n, ap, n); /* A * msb(X) */
  if (cy != 0)
    return 0;

  /* now check B^(2n) - X*A <= A */
  mpn_com_n (tp, tp, 2 * n);
  mpn_add_1 (tp, tp, 2 * n, 1); /* B^(2n) - X*A */
  MPN_ZERO (up, 2 * n);
  MPN_COPY (up, ap, n);
  res = mpn_cmp (tp, up, 2 * n) <= 0;
  TMP_FREE;
  return res;
}
Esempio n. 11
0
mp_limb_t	mpn_sumdiff_n(mp_ptr s,mp_ptr d,mp_srcptr x,mp_srcptr y,mp_size_t n)
{mp_limb_t ret;mp_ptr t;

ASSERT(n>0);
ASSERT_MPN(x,n);ASSERT_MPN(y,n);//ASSERT_SPACE(s,n);ASSERT_SPACE(d,n);
ASSERT(MPN_SAME_OR_SEPARATE_P(s,x,n));
ASSERT(MPN_SAME_OR_SEPARATE_P(s,y,n));
ASSERT(MPN_SAME_OR_SEPARATE_P(d,x,n));
ASSERT(MPN_SAME_OR_SEPARATE_P(d,y,n));
ASSERT(!MPN_OVERLAP_P(s,n,d,n));

if( (s==x && d==y)||(s==y && d==x) )
  {t=__GMP_ALLOCATE_FUNC_LIMBS(n);
   ret=mpn_sub_n(t,x,y,n);
   ret+=2*mpn_add_n(s,x,y,n);
   MPN_COPY(d,t,n);
   __GMP_FREE_FUNC_LIMBS(t,n);
   return ret;}
if(s==x || s==y)
  {ret=mpn_sub_n(d,x,y,n);
   ret+=2*mpn_add_n(s,x,y,n);
   return ret;}
ret=2*mpn_add_n(s,x,y,n);
ret+=mpn_sub_n(d,x,y,n);
return ret;}
Esempio n. 12
0
/* Multiply M by M1 from the right. Since the M1 elements fit in
   GMP_NUMB_BITS - 1 bits, M grows by at most one limb. Needs
   temporary space M->n */
static void
ngcd_matrix_mul_1 (struct ngcd_matrix *M, const struct ngcd_matrix1 *M1)
{
  unsigned row;
  mp_limb_t grow;
  for (row = 0, grow = 0; row < 2; row++)
    {
      mp_limb_t c0, c1;

      /* Compute (u, u') <-- (r00 u + r10 u', r01 u + r11 u') as

	  t   = u
	  u  *= r00
	  u  += r10 * u'
	  u' *= r11
	  u' += r01 * t
      */

      MPN_COPY (M->tp, M->p[row][0], M->n);
      c0 =     mpn_mul_1 (M->p[row][0], M->p[row][0], M->n, M1->u[0][0]);
      c0 += mpn_addmul_1 (M->p[row][0], M->p[row][1], M->n, M1->u[1][0]);
      M->p[row][0][M->n] = c0;

      c1 =     mpn_mul_1 (M->p[row][1], M->p[row][1], M->n, M1->u[1][1]);
      c1 += mpn_addmul_1 (M->p[row][1], M->tp,        M->n, M1->u[0][1]);
      M->p[row][1][M->n] = c1;

      grow |= (c0 | c1);
    }
  M->n += (grow != 0);
  ASSERT (M->n < M->alloc);
}
Esempio n. 13
0
void mpn_invert_trunc(mp_ptr x_new, mp_size_t m, mp_srcptr xp, mp_size_t n, mp_srcptr ap)
{
  mp_ptr tp;
  mp_limb_t cy;
  TMP_DECL;

  TMP_MARK;
  tp = TMP_ALLOC_LIMBS (2 * m);
  
  MPN_COPY(x_new, xp + n - m, m);
  ap += (n - m);

  mpn_mul_n (tp, x_new, ap, m);
  mpn_add_n (tp + m, tp + m, ap, m); /* A * msb(X) */
  
  /* now check B^(2n) - X*A <= A */
  mpn_not (tp, 2 * m);
  mpn_add_1 (tp, tp, 2 * m, 1); /* B^(2m) - X*A */
  
  while (tp[m] || mpn_cmp (tp, ap, m) > 0)
  {
     mpn_add_1(x_new, x_new, m, 1);
     tp[m] -= mpn_sub_n(tp, tp, ap, m);
  }
  TMP_FREE;
}
Esempio n. 14
0
File: neg.c Progetto: mahdiz/mpclib
void
mpf_neg (mpf_ptr r, mpf_srcptr u)
{
  mp_size_t size;

  size = -u->_mp_size;
  if (r != u)
    {
      mp_size_t prec;
      mp_size_t asize;
      mp_ptr rp, up;

      prec = r->_mp_prec + 1;	/* lie not to lose precision in assignment */
      asize = ABS (size);
      rp = r->_mp_d;
      up = u->_mp_d;

      if (asize > prec)
	{
	  up += asize - prec;
	  asize = prec;
	}

      MPN_COPY (rp, up, asize);
      r->_mp_exp = u->_mp_exp;
      size = size >= 0 ? asize : -asize;
    }
  r->_mp_size = size;
}
Esempio n. 15
0
void
_gst_mpz_div_2exp (gst_mpz *w, const gst_mpz *u, unsigned cnt)
{
    mp_size_t usize = u->size;
    mp_size_t wsize;
    mp_size_t abs_usize = ABS (usize);
    mp_size_t limb_cnt;

    limb_cnt = cnt / BITS_PER_MP_LIMB;
    wsize = abs_usize - limb_cnt;
    if (wsize <= 0)
        wsize = 0;
    else
    {
        if (w->alloc < wsize)
            gst_mpz_realloc (w, wsize);

        if (cnt % BITS_PER_MP_LIMB)
            mpn_rshift (w->d, u->d + limb_cnt, abs_usize - limb_cnt,
                        cnt % BITS_PER_MP_LIMB);
        else
            MPN_COPY (w->d, u->d + limb_cnt, abs_usize - limb_cnt);

        wsize -= w->d[wsize - 1] == 0;
    }

    w->size = (usize >= 0) ? wsize : -wsize;
}
Esempio n. 16
0
/*
 * Set f to z, choosing the smallest precision for f
 * so that z = f*(2^BPML)*zs*2^(RetVal)
 */
static int
set_z (mpfr_ptr f, mpz_srcptr z, mp_size_t *zs)
{
  mp_limb_t *p;
  mp_size_t s;
  int c;
  mp_prec_t pf;

  MPFR_ASSERTD (mpz_sgn (z) != 0);

  /* Remove useless ending 0 */
  for (p = PTR (z), s = *zs = ABS (SIZ (z)) ; *p == 0; p++, s--)
    MPFR_ASSERTD (s >= 0);

  /* Get working precision */
  count_leading_zeros (c, p[s-1]);
  pf = s * BITS_PER_MP_LIMB - c;
  if (pf < MPFR_PREC_MIN)
    pf = MPFR_PREC_MIN;
  mpfr_init2 (f, pf);

  /* Copy Mantissa */
  if (MPFR_LIKELY (c))
    mpn_lshift (MPFR_MANT (f), p, s, c);
  else
    MPN_COPY (MPFR_MANT (f), p, s);

  MPFR_SET_SIGN (f, mpz_sgn (z));
  MPFR_SET_EXP (f, 0);

  return -c;
}
Esempio n. 17
0
static void
randiset_lc (gmp_randstate_ptr dst, gmp_randstate_srcptr src)
{
  gmp_rand_lc_struct *dstp, *srcp;

  srcp = (gmp_rand_lc_struct *) RNG_STATE (src);
  dstp = (*__gmp_allocate_func) (sizeof (gmp_rand_lc_struct));

  RNG_STATE (dst) = (void *) dstp;
  RNG_FNPTR (dst) = (void *) &Linear_Congruential_Generator;

  /* _mp_seed and _mp_a might be unnormalized (high zero limbs), but
     mpz_init_set won't worry about that */
  mpz_init_set (dstp->_mp_seed, srcp->_mp_seed);
  mpz_init_set (dstp->_mp_a,    srcp->_mp_a);

  dstp->_cn = srcp->_cn;

  dstp->_cp[0] = srcp->_cp[0];
  if (LIMBS_PER_ULONG > 1)
    dstp->_cp[1] = srcp->_cp[1];
  if (LIMBS_PER_ULONG > 2)  /* usually there's only 1 or 2 */
    MPN_COPY (dstp->_cp + 2, srcp->_cp + 2, LIMBS_PER_ULONG - 2);

  dstp->_mp_m2exp = srcp->_mp_m2exp;
}
Esempio n. 18
0
void _tc4_add_unsigned(mp_ptr rp, mp_size_t * rn, mp_srcptr r1, 
                                   mp_size_t r1n, mp_srcptr r2, mp_size_t r2n)
{
   mp_limb_t cy;
   mp_size_t s1 = r1n;
   mp_size_t s2 = r2n;
   
   if (!s2)
   {
      if (!s1) *rn = 0;
      else
      {
         if (rp != r1) MPN_COPY(rp, r1, s1);
		   *rn = r1n;
		}
   } else
   {
      *rn = r1n;
      cy = mpn_add(rp, r1, s1, r2, s2);
      if (cy) 
      {
         rp[s1] = cy;
         if ((*rn) < 0) (*rn)--;
         else (*rn)++;
      }
   } 
}
Esempio n. 19
0
File: hgcd.c Progetto: qsnake/mpir
/* Multiply M by M1 from the right. Since the M1 elements fit in
   GMP_NUMB_BITS - 1 bits, M grows by at most one limb. Needs
   temporary space M->n */
static void
hgcd_matrix_mul_1 (struct hgcd_matrix *M, const struct hgcd_matrix1 *M1,
           mp_ptr tp)
{
  mp_size_t n0, n1;

  /* Could avoid copy by some swapping of pointers. */
  MPN_COPY (tp, M->p[0][0], M->n);
  n0 = mpn_hgcd_mul_matrix1_vector (M1, M->p[0][0], tp, M->p[0][1], M->n);
  MPN_COPY (tp, M->p[1][0], M->n);
  n1 = mpn_hgcd_mul_matrix1_vector (M1, M->p[1][0], tp, M->p[1][1], M->n);

  /* Depends on zero initialization */
  M->n = MAX(n0, n1);
  ASSERT (M->n < M->alloc);
}
Esempio n. 20
0
void
mpf_init_set (mpf_ptr r, mpf_srcptr s)
{
    mp_ptr rp, sp;
    mp_size_t ssize, size;
    mp_size_t prec;

    prec = __gmp_default_fp_limb_precision;
    r->_mp_d = (mp_ptr) (*__gmp_allocate_func) ((prec + 1) * BYTES_PER_MP_LIMB);
    r->_mp_prec = prec;

    prec++;		/* lie not to lose precision in assignment */
    ssize = s->_mp_size;
    size = ABS (ssize);

    rp = r->_mp_d;
    sp = s->_mp_d;

    if (size > prec)
    {
        sp += size - prec;
        size = prec;
    }

    r->_mp_exp = s->_mp_exp;
    r->_mp_size = ssize >= 0 ? size : -size;

    MPN_COPY (rp, sp, size);
}
Esempio n. 21
0
void
mpz_rootrem (mpz_ptr root, mpz_ptr rem, mpz_srcptr u, unsigned long int nth)
{
  mp_ptr rootp, up, remp;
  mp_size_t us, un, rootn, remn;

  up = PTR(u);
  us = SIZ(u);

  /* even roots of negatives provoke an exception */
  if (us < 0 && (nth & 1) == 0)
    SQRT_OF_NEGATIVE;

  /* root extraction interpreted as c^(1/nth) means a zeroth root should
     provoke a divide by zero, do this even if c==0 */
  if (nth == 0)
    DIVIDE_BY_ZERO;

  if (us == 0)
    {
      if (root != NULL)
	SIZ(root) = 0;
      SIZ(rem) = 0;
      return;
    }

  un = ABS (us);
  rootn = (un - 1) / nth + 1;

  if (root != NULL)
    {
      rootp = MPZ_REALLOC (root, rootn);
      up = PTR(u);
    }
  else
    {
      rootp = __GMP_ALLOCATE_FUNC_LIMBS (rootn);
    }

  MPZ_REALLOC (rem, un);
  remp = PTR(rem);

  if (nth == 1)
    {
      MPN_COPY (rootp, up, un);
      remn = 0;
    }
  else
    {
      remn = mpn_rootrem (rootp, remp, up, un, nth);
    }

  if (root != NULL)
    SIZ(root) = us >= 0 ? rootn : -rootn;
  else
    __GMP_FREE_FUNC_LIMBS (rootp, rootn);

  SIZ(rem) = remn;
}
Esempio n. 22
0
File: set.c Progetto: Cl3Kener/gmp
void
mpq_set (mpq_ptr dest, mpq_srcptr src)
{
  mp_size_t num_size, den_size;
  mp_size_t abs_num_size;
  mp_ptr dp;

  num_size = SIZ(NUM(src));
  SIZ(NUM(dest)) = num_size;
  abs_num_size = ABS (num_size);
  dp = MPZ_NEWALLOC (NUM(dest), abs_num_size);
  MPN_COPY (dp, PTR(NUM(src)), abs_num_size);

  den_size = SIZ(DEN(src));
  SIZ(DEN(dest)) = den_size;
  dp = MPZ_NEWALLOC (DEN(dest), den_size);
  MPN_COPY (dp, PTR(DEN(src)), den_size);
}
Esempio n. 23
0
File: misc.c Progetto: Cl3Kener/gmp
void
mpz_set_n (mpz_ptr z, mp_srcptr p, mp_size_t size)
{
  ASSERT (size >= 0);
  MPN_NORMALIZE (p, size);
  MPZ_REALLOC (z, size);
  MPN_COPY (PTR(z), p, size);
  SIZ(z) = size;
}
Esempio n. 24
0
File: inv.c Progetto: mahdiz/mpclib
void
mpq_inv (MP_RAT *dest, const MP_RAT *src)
{
    mp_size_t num_size = src->_mp_num._mp_size;
    mp_size_t den_size = src->_mp_den._mp_size;

    if (num_size == 0)
        DIVIDE_BY_ZERO;

    if (num_size < 0)
    {
        num_size = -num_size;
        den_size = -den_size;
    }
    dest->_mp_den._mp_size = num_size;
    dest->_mp_num._mp_size = den_size;

    /* If dest == src we may just swap the numerator and denominator, but
       we have to ensure the new denominator is positive.  */

    if (dest == src)
    {
        mp_size_t alloc = dest->_mp_num._mp_alloc;
        mp_ptr limb_ptr = dest->_mp_num._mp_d;

        dest->_mp_num._mp_alloc = dest->_mp_den._mp_alloc;
        dest->_mp_num._mp_d = dest->_mp_den._mp_d;

        dest->_mp_den._mp_alloc = alloc;
        dest->_mp_den._mp_d = limb_ptr;
    }
    else
    {
        den_size = ABS (den_size);
        if (dest->_mp_num._mp_alloc < den_size)
            _mpz_realloc (&(dest->_mp_num), den_size);

        if (dest->_mp_den._mp_alloc < num_size)
            _mpz_realloc (&(dest->_mp_den), num_size);

        MPN_COPY (dest->_mp_num._mp_d, src->_mp_den._mp_d, den_size);
        MPN_COPY (dest->_mp_den._mp_d, src->_mp_num._mp_d, num_size);
    }
}
Esempio n. 25
0
void
mpq_set (MP_RAT *dest, const MP_RAT *src)
{
  mp_size_t num_size, den_size;
  mp_size_t abs_num_size;

  num_size = src->_mp_num._mp_size;
  abs_num_size = ABS (num_size);
  if (dest->_mp_num._mp_alloc < abs_num_size)
    _mpz_realloc (&(dest->_mp_num), abs_num_size);
  MPN_COPY (dest->_mp_num._mp_d, src->_mp_num._mp_d, abs_num_size);
  dest->_mp_num._mp_size = num_size;

  den_size = src->_mp_den._mp_size;
  if (dest->_mp_den._mp_alloc < den_size)
    _mpz_realloc (&(dest->_mp_den), den_size);
  MPN_COPY (dest->_mp_den._mp_d, src->_mp_den._mp_d, den_size);
  dest->_mp_den._mp_size = den_size;
}
Esempio n. 26
0
int
main ()
{
  mp_limb_t nptr[2 * SIZE];
  mp_limb_t dptr[2 * SIZE];
  mp_limb_t qptr[2 * SIZE];
  mp_limb_t pptr[2 * SIZE + 1];
  mp_limb_t rptr[2 * SIZE];
  mp_size_t nsize, dsize, qsize, rsize, psize;
  int test;
  mp_limb_t qlimb;

  for (test = 0; ; test++)
    {
      printf ("%d\n", test);
#ifdef RANDOM
      nsize = random () % (2 * SIZE) + 1;
      dsize = random () % nsize + 1;
#else
      nsize = 2 * SIZE;
      dsize = SIZE;
#endif

      mpn_random2 (nptr, nsize);
      mpn_random2 (dptr, dsize);
      dptr[dsize - 1] |= (mp_limb_t) 1 << (GMP_LIMB_BITS - 1);

      MPN_COPY (rptr, nptr, nsize);
      qlimb = mpn_divrem (qptr, (mp_size_t) 0, rptr, nsize, dptr, dsize);
      rsize = dsize;
      qsize = nsize - dsize;
      qptr[qsize] = qlimb;
      qsize += qlimb;
      if (qsize == 0 || qsize > 2 * SIZE)
	{
	  continue;		/* bogus */
	}
      else
	{
	  mp_limb_t cy;
	  if (qsize > dsize)
	    mpn_mul (pptr, qptr, qsize, dptr, dsize);
	  else
	    mpn_mul (pptr, dptr, dsize, qptr, qsize);
	  psize = qsize + dsize;
	  psize -= pptr[psize - 1] == 0;
	  cy = mpn_add (pptr, pptr, psize, rptr, rsize);
	  pptr[psize] = cy;
	  psize += cy;
	}

      if (nsize != psize || mpn_cmp (nptr, pptr, nsize) != 0)
	abort ();
    }
}
Esempio n. 27
0
mpi_limb_t
mpihelp_mul( mpi_ptr_t prodp, mpi_ptr_t up, mpi_size_t usize,
			      mpi_ptr_t vp, mpi_size_t vsize)
{
    mpi_ptr_t prod_endp = prodp + usize + vsize - 1;
    mpi_limb_t cy;
    struct karatsuba_ctx ctx;

    if( vsize < KARATSUBA_THRESHOLD ) {
	mpi_size_t i;
	mpi_limb_t v_limb;

	if( !vsize )
	    return 0;

	/* Multiply by the first limb in V separately, as the result can be
	 * stored (not added) to PROD.	We also avoid a loop for zeroing.  */
	v_limb = vp[0];
	if( v_limb <= 1 ) {
	    if( v_limb == 1 )
		MPN_COPY( prodp, up, usize );
	    else
		MPN_ZERO( prodp, usize );
	    cy = 0;
	}
	else
	    cy = mpihelp_mul_1( prodp, up, usize, v_limb );

	prodp[usize] = cy;
	prodp++;

	/* For each iteration in the outer loop, multiply one limb from
	 * U with one limb from V, and add it to PROD.	*/
	for( i = 1; i < vsize; i++ ) {
	    v_limb = vp[i];
	    if( v_limb <= 1 ) {
		cy = 0;
		if( v_limb == 1 )
		   cy = mpihelp_add_n(prodp, prodp, up, usize);
	    }
	    else
		cy = mpihelp_addmul_1(prodp, up, usize, v_limb);

	    prodp[usize] = cy;
	    prodp++;
	}

	return cy;
    }

    memset( &ctx, 0, sizeof ctx );
    mpihelp_mul_karatsuba_case( prodp, up, usize, vp, vsize, &ctx );
    mpihelp_release_karatsuba_ctx( &ctx );
    return *prod_endp;
}
Esempio n. 28
0
/* Convert U to REDC form, U_r = B^n * U mod M */
static void
redcify (mp_ptr rp, mp_srcptr up, mp_size_t un, mp_srcptr mp, mp_size_t n, mp_ptr tp)
{
  mp_ptr qp;

  qp = tp + un + n;

  MPN_ZERO (tp, n);
  MPN_COPY (tp + n, up, un);
  mpn_tdiv_qr (qp, rp, 0L, tp, un + n, mp, n);
}
Esempio n. 29
0
static void
gst_mpz_sub_ui (gst_mpz *dif, const gst_mpz *min, mp_limb_t sub)
{
    mp_srcptr minp;
    mp_ptr difp;
    mp_size_t minsize, difsize;
    mp_size_t abs_minsize;

    minsize = min->size;
    abs_minsize = ABS (minsize);

    /* If not space for SUM (and possible carry), increase space.  */
    difsize = abs_minsize + 1;
    if (dif->alloc < difsize)
        gst_mpz_realloc (dif, difsize);

    /* These must be after realloc (ADD1 may be the same as SUM).  */
    minp = min->d;
    difp = dif->d;

    if (sub == 0)
    {
        MPN_COPY (difp, minp, abs_minsize);
        dif->size = minsize;
        return;
    }
    if (abs_minsize == 0)
    {
        difp[0] = sub;
        dif->size = -1;
        return;
    }

    if (minsize < 0)
    {
        difsize = mpn_add_1 (difp, minp, abs_minsize, sub);
        if (difsize != 0)
            difp[abs_minsize] = 1;
        difsize = -(difsize + abs_minsize);
    }
    else
    {
        /* The signs are different.  Need exact comparision to determine
        which operand to subtract from which.  */
        if (abs_minsize == 1 && minp[0] < sub)
            difsize = -(abs_minsize
                        + mpn_sub_1 (difp, &sub, 1, *minp));
        else
            difsize = (abs_minsize
                       + mpn_sub_1 (difp, minp, abs_minsize, sub));
    }

    dif->size = difsize;
}
Esempio n. 30
0
File: misc.c Progetto: Cl3Kener/gmp
void
mpz_init_set_n (mpz_ptr z, mp_srcptr p, mp_size_t size)
{
  ASSERT (size >= 0);

  MPN_NORMALIZE (p, size);
  ALLOC(z) = MAX (size, 1);
  PTR(z) = __GMP_ALLOCATE_FUNC_LIMBS (ALLOC(z));
  SIZ(z) = size;
  MPN_COPY (PTR(z), p, size);
}