コード例 #1
0
ファイル: add_test.c プロジェクト: knikulov/crypto
int
main()
{
	ec_point x, y, z;
	mpl_int p, a;
	char buf[80];

	if (ec_initv(&x, &y, &z, NULL) != MPL_OK) {
		printf("can't init points");
		return 1;
	}

	if (mpl_initv(&p, &a, NULL) != MPL_OK) {
		printf("can't init ints\n");
		goto err_init;
	}

	mpl_set_sint(&(x.x), XX);
	mpl_set_sint(&(x.y), XY);
	mpl_set_sint(&(y.x), YX);
	mpl_set_sint(&(y.y), YY);
	mpl_set_sint(&p, 5);
	mpl_set_sint(&a, 4);

	if (ec_add(&z, &x, &y, &a, &p) != MPL_OK) {
		printf("addition error\n");
		goto error;
	}

	printf("(%i,%i) + (%i,%i) = ", XX, XY, YX, YY);
	if (mpl_to_str(&(z.x), buf, 10, 80) != MPL_OK) {
		printf("can't convert mpl_int\n");
		goto error;
	}

	printf("(%s,", buf);

	if (mpl_to_str(&(z.y), buf, 10, 80) != MPL_OK) {
		printf("can't convert mpl_int\n");
		goto error;
	}

	printf("%s)\n", buf);

error:
	mpl_clearv(&p, &a, NULL);
err_init:
	ec_clearv(&x, &y, &z, NULL);

	return 0;
}
コード例 #2
0
ファイル: mod_exp_simple_test.c プロジェクト: dzruyk/libmpl
int 
main(int argc, const char *argv[])
{
	mpl_int a, b, c, d;

	mpl_initv(&a, &b, &c, &d, NULL);

	mpl_set_sint(&a, 1000000);
	mpl_set_sint(&b, 1);
	mpl_set_sint(&c, 455);

	test_mod_exp(&d, &a, &b, &c);

	mpl_clearv(&a, &b, &c, &d, NULL);

	return 0;
}
コード例 #3
0
ファイル: mpl_mod_exp.c プロジェクト: dzruyk/libmpl
int
mpl_mod_exp(mpl_int *c, const mpl_int *a, const mpl_int *y, const mpl_int *b)
{

	mpl_int w[MPL_MODEXP_STACK];
	mpl_int e, s, mu, z;
	_mpl_int_t *dp, buffer;
	int i, k, nbits, rc;
	int do_single;
	unsigned int mask, x, n, tmp, cnt;

	if ((rc = mpl_initv(&e, &s, &mu, &z, NULL)) != MPL_OK)
		return rc;

	if (mpl_isneg(y)) {
		if ((rc = mpl_mod_inv(&z, a, b)) != MPL_OK)
			goto end;
	} else {
		if ((rc = mpl_copy(&z, a)) != MPL_OK)
			goto end;
	}

	n = mpl_nr_bits(y);

	if (n <= 7)
		k = 2;
	else if (n <= 36)
		k = 3;
	else if (n <= 140)
		k = 4;
	else if (n <= 450)
		k = 5;
	else if (n <= 1303)
		k = 6;
	else if (n <= 3529)
		k = 7;
	else
		k = 8;

	cnt = 0;

	for (i = 0; i < 1 << (k-1); i++) {
		rc = mpl_init(&w[i]);
		if (rc != MPL_OK) {
			for (i = 0; i < cnt; i++)
				mpl_clear(&w[i]);
			goto end;
		}
		++cnt;
	}

	/* reduce Z */
	rc = mpl_div(NULL, &z, &z, b);
	if (rc != MPL_OK)
		goto err;

	/* e = a */
	rc = mpl_copy(&e, &z);
	if (rc != MPL_OK)
		goto err;

	/* c = 1 */
	mpl_set_one(&s);

	/* prepare reduction constant */
	rc = mpl_reduce_barrett_setup(&mu, b);
	if (rc != MPL_OK)
		goto err;

	/* e = a^{2^(k-1)} */
	for (i = 0; i < k-1; i++) {
		rc = mpl_sqr(&e, &e);
		if (rc != MPL_OK)
			goto err;
		rc = mpl_reduce_barrett(&e, &e, b, &mu);
		if (rc != MPL_OK)
			goto err;
	}

	/* Now fill precomputed table. */
	rc = mpl_copy(&w[0], &e);
	if (rc != MPL_OK)
		goto err;

	for (i = 1; i < 1 << (k-1); i++) {
		/* w[i] = (w[i-1] * a) mod b */
		rc = mpl_mul(&w[i], &w[i-1], &z);
		if (rc != MPL_OK)
			goto err;
		rc = mpl_reduce_barrett(&w[i], &w[i], b, &mu);
		if (rc != MPL_OK)
			goto err;
	}
	
	buffer = nbits = do_single = cnt = 0;

	/* Count bits of the topmost MP integer digit. */
	dp = y->dig + y->top;
	tmp = *dp;
	for (cnt = 0; tmp > 0; cnt++)
		tmp >>= 1;
	nbits = cnt;
	buffer = *dp--;

	/* Precalculated window mask. */
	mask = (1 << k) - 1;

	while (n > 0) {
		unsigned int left, xmask;

		if (nbits == 0) {
			buffer = *dp--;
			nbits = MPL_INT_BITS;
		}

		/* Check most significant bit of the bit buffer. */
		if ((buffer & (1 << (nbits-1))) == 0) {
			/* c = c^2 mod b */
			rc = mpl_sqr(&s, &s);
			if (rc != MPL_OK)
				goto err;

			rc = mpl_reduce_barrett(&s, &s, b, &mu);
			if (rc != MPL_OK)
				goto err;

			--nbits;
			--n;
			continue;
		}

		if (nbits >= k) {
			/* We have enough bits in the buffer to fill window. */
			x = (buffer & (mask << (nbits-k))) >> (nbits-k);
			nbits -= k;
			n -= k;
		} else {
コード例 #4
0
ファイル: mpl_gcd.c プロジェクト: knikulov/libmpl
int
mpl_gcd(mpl_int *c, const mpl_int *a, const mpl_int *b)
{
    mpl_int x, y, u, v;
    int rc, k;

    if ((rc = mpl_initv(&u, &v, NULL)) != MPL_OK)
        return rc;

    x.dig = a->dig;
    x.alloc = a->alloc;
    x.top = a->top;
    x.sign = MPL_SIGN_POS;

    y.dig = b->dig;
    y.alloc = b->alloc;
    y.top = b->top;
    y.sign = MPL_SIGN_POS;

    rc = mpl_copy(&u, &x);
    if (rc != MPL_OK)
        goto err;

    rc = mpl_copy(&v, &y);
    if (rc != MPL_OK)
        goto err;

    k = 0;
    while (mpl_iseven(&v) && mpl_iseven(&u)) {
        rc = mpl_shr(&u, 1);
        if (rc != MPL_OK)
            goto err;
        rc = mpl_shr(&v, 1);
        if (rc != MPL_OK)
            goto err;
        ++k;
    }

    do {
        /* Reduce u by factor of two. */
        while (mpl_iseven(&u)) {
            rc = mpl_shr(&u, 1);
            if (rc != MPL_OK)
                goto err;
        }

        /* Reduce v by factor of two. */
        while (mpl_iseven(&v)) {
            rc = mpl_shr(&v, 1);
            if (rc != MPL_OK)
                goto err;
        }

        /* Reduce greatest of u or v. */
        if (mpl_cmp(&u, &v) != MPL_CMP_LT) {
            /* u = (u - v) / 2 */
            rc = mpl_sub(&u, &u, &v);
            if (rc != MPL_OK)
                goto err;
            rc = mpl_shr(&u, 1);
            if (rc != MPL_OK)
                goto err;
        } else {
            /* v = (v - u) / 2 */
            rc = mpl_sub(&v, &v, &u);
            if (rc != MPL_OK)
                goto err;
            rc = mpl_shr(&v, 1);
            if (rc != MPL_OK)
                goto err;
        }

    } while (!mpl_iszero(&u) && !mpl_iszero(&v));

    if (mpl_iszero(&u)) {
        rc = mpl_copy(c, &v);
        if (rc != MPL_OK)
            goto err;
    } else {
        rc = mpl_copy(c, &u);
        if (rc != MPL_OK)
            goto err;
    }

    if (k > 0) {
        rc = mpl_shl(c, k);
        if (rc != MPL_OK)
            goto err;
    }

    rc = MPL_OK;
err:
    mpl_clearv(&u, &v, NULL);
    return rc;
}
コード例 #5
0
ファイル: mpl_primality.c プロジェクト: dzruyk/libmpl
int
mpl_primality_miller_rabin(const mpl_int *m, int r,
			  int (*rnd)(void *buf, size_t size, void *rndctx),
			  void *rndctx)
{
	mpl_int m_minus_one, one;
	mpl_int m_mod, a, t, x, mu;
	int i, rc, s, n;

	if (rnd == NULL || r == 0 || mpl_iszero(m))
		return MPL_ERR;

	rc = mpl_initv(&m_minus_one, &one, &a, &t, &x, &mu, NULL);
	if (rc != MPL_OK)
		return rc;
	/* m_mod = |m| */
	m_mod.dig = m->dig;
	m_mod.top = m->top;
	m_mod.sign = MPL_SIGN_POS;
	m_mod.alloc = 0;

	/* one = 1, m_minus_one = |m| - 1 */
	mpl_set_one(&one);

	rc = mpl_sub(&m_minus_one, &m_mod, &one);
	if (rc != MPL_OK)
		goto out;

	/* Prepare Barrett reduction precalculated constant. */
	rc = mpl_reduce_barrett_setup(&mu, &m_mod);
	if (rc != MPL_OK)
		goto out;

	/* Determine power of two used to construct |m|-1 = 2^s * t. */
	s = 0;
	n = m_minus_one.top + 1;

	for (i = 0; i < n; i++) {
		_mpl_int_t dig;
		int cnt;

		dig = m_minus_one.dig[i];

		for (cnt = 0; cnt < MPL_INT_BITS; cnt++) {
			if (dig & 0x1)
				goto brk_loop;
			dig >>= 1;
			++s;
		}
	}

brk_loop:

	/* The following condition is a paranoidal check. */
	if (i >= n) {
		rc = MPL_ERR;
		goto out;
	}

	/* m_minus_one = 2^s * t */
	rc = mpl_copy(&t, &m_minus_one);
	if (rc != MPL_OK)
		goto out;

	if (s > 0) {
		rc = mpl_shr(&t, s);
		if (rc != MPL_OK)
			goto out;
	}

	/* Number of random bytes one digit less than m. */
	n = (m->top * MPL_INT_BITS) / CHAR_BIT;

	for (i = 0; i < r; i++) {
		int j;

		//rc = mpl_random(&a, n, rnd, rndctx);
		rc = mpl_rand_below(&a, &m_minus_one, rnd, rndctx);
		if (rc != MPL_OK)
			goto out;

		rc = mpl_mod_exp(&x, &a, &t, &m_mod);
		if (rc != MPL_OK)
			goto out;

		if (mpl_cmp(&x, &one) == MPL_CMP_EQ)
			continue;

		if (mpl_cmp(&x, &m_minus_one) == MPL_CMP_EQ)
			continue;

		for (j = 1; j < s; j++) {
			
			rc = mpl_sqr(&x, &x);
			if (rc != MPL_OK)
				goto out;

			rc = mpl_reduce_barrett(&x, &x, &m_mod, &mu);
			if (rc != MPL_OK)
				goto out;

			if (mpl_isone(&x)) {
				rc = MPL_COMPOSITE;
				goto out;
			}

			if (mpl_cmp(&x, &m_minus_one) == MPL_CMP_EQ)
				break;
		}

		if (j >= s) {
			rc = MPL_COMPOSITE;
			goto out;
		}
	}

	rc = MPL_OK;
out:
	mpl_clearv(&m_minus_one, &one, &a, &t, &x, &mu, NULL);
	return rc;
}