[完整版]C语言实现RSA加解密

更正一些:这是在dev-c++里面写的,程序里面定义的int,数据不够大,如果想要大一些的,把p,q,n,e,t之类的都改成long long型,别忘了改解密函数decrypt()里面的zhuan1. 也可以改成python实现,因为python可以处理超长的数据。


想要看更详细说明可以访问我的另一篇博客:C语言实现RSA加解密

完善的内容有:
判断输入的p、q是否是素数:
将gcd()改成bool函数;
还有一些输入不符合条件的处理
这里奉上完整代码:

#include<stdio.h>
#include<string.h>
int changdu; 
int c[100];
//判断两个数是不是互素。 
bool gcd(int p,int q){
	int temp1,temp2;   //q=temp2*p+temp1 ;
	if(q<p){
		temp1=p;
		p=q;
		q=temp1;
	}
	temp1=q%p,temp2=q/p; 
	while(temp1!=0){
		
	    q=p;p=temp1;
		temp1=q%p;temp2=q/p;
		}
		if(temp1==0&&temp2==q){
			printf("符合条件!\n");
			return true;
	    }
	    else{
	    	printf("不符合条件!请重新输入:\n");
	    	return false;
		}
}

//求e关于模(p-1)(q-1)的逆元d:即私钥 
int extend(int e,int t){
	int d;
	for(d=0;d<t;d++){
		if(e*d%t==1)
	        return d;
	}
}

//判断输入的p和q是不是素数 
bool is_sushu(int s){
	for(int i=2;i<s;i++){
		if(s%i==0) return false;
	}
	return true;
}
//将明文转换成数字明文 
//void convert(){
//	char mingwen[100];    //符号明文 
//	printf("请输入明文:\n");
//	gets(mingwen);
//	changdu=strlen();
//	int ming[changdu];   //定义符号明文 
//	for(int i=0;i<changdu;i++){
//	ming[i]=mingwen[i];        //将字母转换成对应的ascii码。 
//	printf("%d",mingwen[i]);
//	} 
//	 
//	
//}


//加密函数 
void encrypt(int e,int n){       //自己指定指数e 

    //先将符号明文转换成字母所对应的ascii码。 
	char mingwen[100];    //符号明文 
	printf("请输入明文:\n");
	scanf("%s",mingwen);
	//gets(mingwen);
	changdu=strlen(mingwen);
	int ming[strlen(mingwen)];   //定义符号明文 
	for(int i=0;i<strlen(mingwen);i++){
	ming[i]=mingwen[i];        //将字母转换成对应的ascii码。 
	printf("%d",mingwen[i]);  //将字母转换成对应的ascii码。可以不打印 
	} 
	printf("\n"); 
	//开始加密 
	printf("加密开始…………………………\n");
	int zhuan=1;    //c为加密后的数字密文 
	for(int i=0;i<strlen(mingwen);i++){
	 
	   for(int j=0;j<e;j++){
		zhuan=zhuan*ming[i]%n;
		//zhuan=zhuan%n; 
	   }
	   c[i]=zhuan;
	   //printf("%d",mi[i]); 
	   zhuan=1;
	} 
	printf("加密密文为:\n");
	for(int i=0;i<strlen(mingwen);i++) 
	printf("%d",c[i]); 
	printf("\n加密结束…………………………\n");
	//以下写法会导致溢出!
//	{
//		for(int i=0;i<strlen(mingwen);i++){
//		zhuan=pow()
//		mi[i]=int(pow(ming[i],e))%n;
//		printf("密文为:%d",mi[0]);
//	}
//	} 
	
	
//	printf("密文为:\n");
//	for(int i=0;i<strlen(mingwen);i++){
//		printf("%d",mi[i]);
//	}
	
} 


//解密函数 
void decrypto(int d,int n){
	int de_mingwen[changdu],zhuan1=1;
	char de_ming[changdu];
	for(int i=0;i<changdu;i++){
	 
	   for(int j=0;j<d;j++){
		zhuan1=zhuan1*c[i]%n;
		//zhuan=zhuan%n; 
	   }
	   de_mingwen[i]=zhuan1;
	   //printf("%d",mi[i]); 
	   zhuan1=1;
	} 
	printf("解密开始…………………………\n");
	printf("解密后的数字明文为:\n");
	for(int i=0;i<changdu;i++) 
	printf("%d",de_mingwen[i]); 
	printf("\n");
	printf("解密后的符号明文为:\n");
	for(int i=0;i<changdu;i++){
		de_ming[i]=de_mingwen[i];
		printf("%c",de_ming[i]);
	}
	printf("\n解密结束…………………………\n");
}


int main(){
	int q,p,e,d,n,t,x,tep;
	while(1){
	printf("请输入p:",p);scanf("%d",&p);
	tep=is_sushu(p);
	if(tep==0){
		printf("p不是素数,请重新输入p!\n");
		continue;
	}  
	printf("请输入q:",q);scanf("%d",&q);
	tep=is_sushu(q);
	if(tep==0){
		printf("q不是素数,请重新输入q!\n");
		printf("请输入q:",q);scanf("%d",&q);
	    tep=is_sushu(q);
	}  
	n=q*p;
	t=(q-1)*(p-1); 
	tep=gcd(p,q);
	if(tep==0)  continue;
    printf("t=(q-1)*(p-1)=%d\n",t);
	printf("请输入一个指数e,使得(e,t)=1\n");scanf("%d",&e);
	tep=gcd(e,t);
	while(tep==0){
	printf("请重新输入一个指数e,使得(e,t)=1:");scanf("%d",&e);
	tep=gcd(e,t);	
	}
	d=extend(e,t); 
	printf("密钥为:%d,一定保管好!",d);
	printf("\n\n~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\n");
	encrypt(e,n);
	printf("\n请输入正确的密钥,密钥正确将解密上面的密文:");scanf("%d",&d);
	decrypto(d,n);
	printf("\n~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\n");
	}
	
	return 0;
}

执行结果如图:
在这里插入图片描述

加密是根据转换成符号对应的ascii码进行的,所以输入没有那么多限制,可以包括空格啊标点符号之类的,可读性更高!

  • 22
    点赞
  • 217
    收藏
    觉得还不错? 一键收藏
  • 13
    评论
好的,以下是用C语言实现RSA加解密算法的示例代码: ```c #include <stdio.h> #include <stdlib.h> #include <string.h> #include <time.h> #include <math.h> #include <stdint.h> // 定义大质数素数数组,数组长度为100 uint32_t PrimeList[100] = { 2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37, 41, 43, 47, 53, 59, 61, 67, 71, 73, 79, 83, 89, 97, 101, 103, 107, 109, 113, 127, 131, 137, 139, 149, 151, 157, 163, 167, 173, 179, 181, 191, 193, 197, 199, 211, 223, 227, 229, 233, 239, 241, 251, 257, 263, 269, 271, 277, 281, 283, 293, 307, 311, 313, 317, 331, 337, 347, 349, 353, 359, 367, 373, 379, 383, 389, 397, 401, 409, 419, 421, 431, 433, 439, 443, 449, 457, 461, 463, 467, 479, 487, 491, 499, 503, 509, 521, 523, 541 }; // 定义欧拉函数,参数为两个质数 uint32_t Euler(uint32_t p, uint32_t q) { return (p - 1) * (q - 1); } // 定义取模反元素函数 uint32_t ModInverse(uint32_t a, uint32_t b) { uint32_t r, r1 = a, r2 = b; uint32_t t, t1 = 0, t2 = 1; while (r2 > 0) { t = r1 / r2; r = r1 - t * r2; r1 = r2; r2 = r; t = t1 - t * t2; t1 = t2; t2 = t; } if (r1 == 1) { if (t1 < 0) { t1 += a; } return t1; } else { return 0; } } // 定义素数判断函数 int IsPrime(uint32_t n) { int i; if (n < 2) { return 0; } for (i = 0; i < 100; i++) { if (n == PrimeList[i]) { return 1; } if (n % PrimeList[i] == 0) { return 0; } } for (i = 251; i <= sqrt(n); i += 2) { if (n % i == 0) { return 0; } } return 1; } // 定义随机生成素数函数 uint32_t RandomPrime() { uint32_t p; do { p = rand() % 65536 + 32768; } while (!IsPrime(p)); return p; } // 定义生成RSA密钥对函数 void RSAKeyGen(uint32_t *p, uint32_t *q, uint32_t *n, uint32_t *e, uint32_t *d) { srand((unsigned)time(NULL)); *p = RandomPrime(); *q = RandomPrime(); *n = *p * *q; uint32_t phi = Euler(*p, *q); do { *e = rand() % phi; } while (*e < 2 || *e >= phi || phi % *e == 0); *d = ModInverse(phi, *e); } // 定义RSA加密函数 uint32_t RSAEncrypt(uint32_t m, uint32_t e, uint32_t n) { uint32_t c = 1; for (int i = 0; i < e; i++) { c = (c * m) % n; } return c; } // 定义RSA解密函数 uint32_t RSADecrypt(uint32_t c, uint32_t d, uint32_t n) { uint32_t m = 1; for (int i = 0; i < d; i++) { m = (m * c) % n; } return m; } int main() { uint32_t p, q, n, e, d; RSAKeyGen(&p, &q, &n, &e, &d); printf("p = %u, q = %u, n = %u, e = %u, d = %u\n", p, q, n, e, d); uint32_t m = 12345; printf("m = %u\n", m); uint32_t c = RSAEncrypt(m, e, n); printf("c = %u\n", c); uint32_t m2 = RSADecrypt(c, d, n); printf("m2 = %u\n", m2); return 0; } ``` 这段代码包括随机生成素数、生成RSA密钥对、RSA加密、RSA解密等多个函数。通过调用这些函数,可以实现RSA加解密算法

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 13
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值