示例#1
0
static void select_point(mpz_t x, mpz_t y, mpz_t a, mpz_t b, mpz_t N,
                         mpz_t t, mpz_t t2)
{
  mpz_t Q, t3, t4;
  gmp_randstate_t* p_randstate = get_randstate();

  mpz_init(Q); mpz_init(t3); mpz_init(t4);
  mpz_set_ui(y, 0);

  while (mpz_sgn(y) == 0) {
    /* select a Q s.t. (Q,N) != -1 */
    do {
      do {
        /* mpz_urandomm(x, *p_randstate, N); */
        mpz_urandomb(x, *p_randstate, 32);   /* May as well make x small */
        mpz_mod(x, x, N);
      } while (mpz_sgn(x) == 0);
      mpz_mul(t, x, x);
      mpz_add(t, t, a);
      mpz_mul(t, t, x);
      mpz_add(t, t, b);
      mpz_mod(Q, t, N);
    } while (mpz_jacobi(Q, N) == -1);
    /* Select Y */
    sqrtmod(y, Q, N, t, t2, t3, t4);
    /* TODO: if y^2 mod Ni != t, return composite */
    if (mpz_sgn(y) == 0) croak("y == 0 in point selection\n");
  }
  mpz_clear(Q); mpz_clear(t3); mpz_clear(t4);
}
示例#2
0
/* See Cohen 1.5.3 */
int modified_cornacchia(mpz_t x, mpz_t y, mpz_t D, mpz_t p)
{
    int result = 0;
    mpz_t a, b, c, d;

    if (mpz_cmp_ui(p, 2) == 0) {
        mpz_add_ui(x, D, 8);
        if (mpz_perfect_square_p(x)) {
            mpz_sqrt(x, x);
            mpz_set_ui(y, 1);
            result = 1;
        }
        return result;
    }
    if (mpz_jacobi(D, p) == -1)     /* No solution */
        return 0;

    mpz_init(a);
    mpz_init(b);
    mpz_init(c);
    mpz_init(d);

    sqrtmod(x, D, p, a, b, c, d);
    if ( (mpz_even_p(D) && mpz_odd_p(x)) || (mpz_odd_p(D) && mpz_even_p(x)) )
        mpz_sub(x, p, x);

    mpz_mul_ui(a, p, 2);
    mpz_set(b, x);
    mpz_sqrt(c, p);
    mpz_mul_ui(c, c, 2);

    /* Euclidean algorithm */
    while (mpz_cmp(b, c) > 0) {
        mpz_set(d, a);
        mpz_set(a, b);
        mpz_mod(b, d, b);
    }

    mpz_mul_ui(c, p, 4);
    mpz_mul(a, b, b);
    mpz_sub(a, c, a);   /* a = 4p - b^2 */
    mpz_abs(d, D);      /* d = |D| */

    if (mpz_divisible_p(a, d)) {
        mpz_divexact(c, a, d);
        if (mpz_perfect_square_p(c)) {
            mpz_set(x, b);
            mpz_sqrt(y, c);
            result = 1;
        }
    }

    mpz_clear(a);
    mpz_clear(b);
    mpz_clear(c);
    mpz_clear(d);

    return result;
}
/*===========================================================================
   Tonelli-Shanks:

   Function: Performs Tonelli-Shanks on n mod every prime in the factor base

===========================================================================*/
static void tonelliShanks(unsigned long numPrimes, mpz_t n, mpz_t * sqrts)
{
  unsigned long i;
  mpz_t fbprime, t1, t2, t3, t4;

  mpz_init(fbprime);
  mpz_init(t1); mpz_init(t2); mpz_init(t3); mpz_init(t4);

  mpz_set_ui(sqrts[0], 0);
  for (i = 1; i < numPrimes; i++) {
    mpz_set_ui(fbprime, factorBase[i]);
    sqrtmod(sqrts[i], n, fbprime, t1, t2, t3, t4);
  }
  mpz_clear(t1); mpz_clear(t2); mpz_clear(t3); mpz_clear(t4);
  mpz_clear(fbprime);
}
示例#4
0
/* See Cohen 1.5.2 */
int cornacchia(mpz_t x, mpz_t y, mpz_t D, mpz_t p)
{
    int result = 0;
    mpz_t a, b, c, d;

    if (mpz_jacobi(D, p) < 0)     /* No solution */
        return 0;

    mpz_init(a);
    mpz_init(b);
    mpz_init(c);
    mpz_init(d);

    sqrtmod(x, D, p, a, b, c, d);
    mpz_set(a, p);
    mpz_set(b, x);
    mpz_sqrt(c, p);

    while (mpz_cmp(b,c) > 0) {
        mpz_set(d, a);
        mpz_set(a, b);
        mpz_mod(b, d, b);
    }

    mpz_mul(a, b, b);
    mpz_sub(a, p, a);   /* a = p - b^2 */
    mpz_abs(d, D);      /* d = |D| */

    if (mpz_divisible_p(a, d)) {
        mpz_divexact(c, a, d);
        if (mpz_perfect_square_p(c)) {
            mpz_set(x, b);
            mpz_sqrt(y, c);
            result = 1;
        }
    }

    mpz_clear(a);
    mpz_clear(b);
    mpz_clear(c);
    mpz_clear(d);

    return result;
}
示例#5
0
void findPointProj(pointProj pt, giant seed, curveParams *cp)
/* Starting with seed, finds a random (projective) point {x,y,1} on curve.
 */
{
	giant x = pt->x, y = pt->y, z = pt->z;

	CKASSERT(cp->curveType == FCT_Weierstrass);
	feemod(cp, seed);
    	while(1) {
		gtog(seed, x);
		gsquare(x); feemod(cp, x);	// x := seed^2
		addg(cp->a, x);			// x := seed^2 + a
		mulg(seed,x); 			// x := seed^3 + a*seed
		addg(cp->b, x);
		feemod(cp, x);			// x := seed^3 + a seed + b.
		/* test cubic form for having root. */
		if(sqrtmod(x, cp)) break;
		iaddg(1, seed);
	}
	gtog(x, y);
    	gtog(seed,x);
	int_to_giant(1, z);
}