hust 密碼學課設 rsa引數d

cxzzzznb發表於2020-10-07

hust密碼學課設 rsa引數d,

在這裡插入圖片描述

#include <stdio.h>
#include <gmpxx.h>
#include<time.h>   
#include<stdlib.h>
#pragma warning (disable:4996)


mpz_class modmod(mpz_class a, mpz_class m, mpz_class n)
{
	mpz_class  result = 1;

	while (m != 0) {

		if ((m & 1) == 1) {
			result = (result * a) % n;
		}
		a = (a * a) % n;
		m = m>>1;
	}
	return result;
}
//求最大公因數
mpz_class maxgcd(mpz_class a, mpz_class b)
{

	while (1)
	{
		while (a > b)
			a = a - b;
		if (a < b)
		{
			b = b - a;
			continue;
		}
		else
			return a;
	}
}

//求引數d
mpz_class rsad(mpz_class e, mpz_class m)
{
	mpz_class x1, x2, x3, y1, y2, y3, t1, t2, t3, q;
	x1 = y2 = 1;
	x2 = y1 = 0;
	x3 = (e >= m) ? e : m;
	y3 = (e >= m) ? m : e;
	while (1)
	{
		if (y3 == 0)
			return 0;
		if (y3 == 1)
			return y2;
		q = x3 / y3;
		t1 = x1 - q * y1;
		t2 = x2 - q * y2;
		t3 = x3 - q * y3;
		x1 = y1;
		x2 = y2;
		x3 = y3;
		y1 = t1;
		y2 = t2;
		y3 = t3;
	}
}

//素性檢測
int pjudge(mpz_class n)
{
	mpz_class a, b, m, r;
	m = n - 1;
	int i, k = 0;
	while ((m % 2) != 0) {
		m >>= 2;
		k++;

	}
	//隨機數生成
	gmp_randstate_t rstate;
	gmp_randinit_default(rstate);
	gmp_randseed_ui(rstate, time(NULL));
	mpz_class n1 = n - 1;
	mpz_urandomm(a.get_mpz_t(), rstate, n1.get_mpz_t());
	a = a + 1;
	b = modmod(a, m, n);//a的m次方模n
	if ((b % n) == 1)
		return 1;
	for (i = 0; i < k; i++) {
		if ((b % n) == ((-1) % n))
			return 1;
		else
			b = (b * b) % n;
	}
	return 0;
}


int main()
{
	int n, i;
	mpz_class e, p, q, m, d;
	scanf("%d", &n);
	for (i = 0; i < n; i++)//問題的個數
	{

		gmp_scanf("%Zd %Zd %Zd", e.get_mpz_t(), p.get_mpz_t(), q.get_mpz_t());
		m = (p - 1) * (q - 1);

		if (e<65536)
		{
			printf("ERROR\n");
			continue;
		}//判斷e不能太小

		//判斷是否素數
		if (pjudge(p)==0)
		{
			printf("ERROR\n");
			continue;
		}
		if (pjudge(q)==0)
		{
			printf("ERROR\n");
			continue;
		}
		//pq間隔不能太小
		if (abs(p - q) <65536)
		{
			printf("ERROR\n");
			continue;
		}
		//p-1和q-1不能太平滑
		mpz_class maxg = maxgcd((p - 1), (q - 1));
		if (maxg > 20)
		{
			printf("ERROR\n");
			continue;
		}

		if (gcd(e,m)!=1)
		{
			printf("ERROR\n");
			continue;
		}
		//求d
		d = rsad(e, m);
		gmp_printf("%Zd\n", d.get_mpz_t());
	}

}

看了看別人的程式碼
再看下自己的
wtcl
`

相關文章