⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 sdes.cpp

📁 用C语言简单实现了simple版本的DES密码的加密和解密
💻 CPP
字号:
#include<stdio.h>
#include<string.h>
#include<malloc.h>
#include<math.h>

float x=10;

void leftshift(int *c){
	int temp,i;
	temp=*(c+0);
	for(i=0;i<4;i++)*(c+i)=*(c+i+1);
	*(c+4)=temp;
}

int CharToInt(char K[10]){
	int len_K,i,num=0;
	len_K=strlen(K);
	printf("%d\n",len_K);
	for(i=0;i<len_K;i++)
	{
		num=num+(K[i]-48)*pow(x,len_K-i-1);
	}
	return num;
}

void GenerKey(int key[],int **k){
	int q[10],i;
	//PC-1
	q[0]=key[2];q[1]=key[4];q[2]=key[1];q[3]=key[6];
	q[4]=key[3];q[5]=key[9];q[6]=key[0];q[7]=key[8];
	q[8]=key[7];q[9]=key[5];
	leftshift(q);leftshift(&q[5]);//第一个密钥左移一位
	k[0][0]=q[5];k[0][1]=q[2];k[0][2]=q[6];k[0][3]=q[3];
	k[0][4]=q[7];k[0][5]=q[4];k[0][6]=q[9];k[0][7]=q[8];
	for(i=0;i<2;i++){			  //第二个密钥左移两位
		leftshift(q);leftshift(&q[5]);
	}
	//PC-2
	k[1][0]=q[5];k[1][1]=q[2];k[1][2]=q[6];k[1][3]=q[3];
	k[1][4]=q[7];k[1][5]=q[4];k[1][6]=q[9];k[1][7]=q[8];
}

void FBox(int *a,int *key){
	int q[8],b[4],i,j,m,n;
	float z=2;
	//EBOX
	q[0]=a[3];q[1]=a[0];q[2]=a[1];q[3]=a[2];
	q[4]=a[1];q[5]=a[2];q[6]=a[3];q[7]=a[0];
	//将经过EBOX的二进制序列与密钥序列异或
	for(i=0;i<8;i++)q[i]=(q[i]+key[i])%2;
	//SBOX
	int Sbox0[4][4]={{1,0,2,3},{3,1,0,2},{2,0,3,1},{1,3,2,0}},
		Sbox1[4][4]={{0,3,1,2},{3,2,0,1},{1,0,3,2},{2,1,3,0}};
	i=q[0]*pow(z,1)+q[3]*pow(z,0);j=q[1]*pow(z,1)+q[2]*pow(z,0);
	b[1]=Sbox0[i][j]%2;b[0]=(Sbox0[i][j]/2)%2;
	m=q[4]*pow(z,1)+q[7]*pow(z,0);n=q[5]*pow(z,1)+q[6]*pow(z,0);
	b[3]=Sbox1[m][n]%2;b[2]=(Sbox1[m][n]/2)%2;
	//PBOX
	a[0]=b[1];a[1]=b[3];a[2]=b[2];a[3]=b[0];
}

void DES(int *a,int key[8][8]){
	int q[8],p[8],i,j;
	//IP
	q[0]=a[1];q[1]=a[5];q[2]=a[2];q[3]=a[0];
	q[4]=a[3];q[5]=a[7];q[6]=a[4];q[7]=a[6];
	for(i=0;i<2;i++){//SDES的两轮操作
		for(j=0;j<8;j++)p[j]=q[j];
		FBox(&p[4],key[i]);
		for(j=0;j<4;j++)q[j]=q[j+4];
		for(j=0;j<4;j++)q[j+4]=(p[j+4]+p[j])%2;
	}
	//IP逆
	a[0]=q[3];a[1]=q[0];a[2]=q[2];a[3]=q[4];
	a[4]=q[6];a[5]=q[1];a[6]=q[7];a[7]=q[5];	
}

void Encrypht(){
	char plaintext[1000];
	char ciphertext[1000];
	float z=2;
	int key[10],numkey,i,j,len_plaint,*binary_plaint,m,k[8][8];
	char K[10];


	FILE *fp;char filename[30];
	printf("给文件加密输入1,直接加密输入2:");
	scanf("%d",&m);   //选择对文件加密还是直接加密	
	printf("输入一个0--1023的密钥:");
	scanf("%s",K);
	numkey=CharToInt(K);
	printf("%d\n",numkey);
	for(i=9;i>=0;i--){key[i]=numkey%2;numkey=numkey/2;}


	int q[10];
	//PC-1
	q[0]=key[2];q[1]=key[4];q[2]=key[1];q[3]=key[6];
	q[4]=key[3];q[5]=key[9];q[6]=key[0];q[7]=key[8];
	q[8]=key[7];q[9]=key[5];
	leftshift(q);leftshift(&q[5]);//第一个密钥左移一位
	k[0][0]=q[5];k[0][1]=q[2];k[0][2]=q[6];k[0][3]=q[3];
	k[0][4]=q[7];k[0][5]=q[4];k[0][6]=q[9];k[0][7]=q[8];
	for(i=0;i<2;i++){			  //第二个密钥左移两位
		leftshift(q);leftshift(&q[5]);
	}
	//PC-2
	k[1][0]=q[5];k[1][1]=q[2];k[1][2]=q[6];k[1][3]=q[3];
	k[1][4]=q[7];k[1][5]=q[4];k[1][6]=q[9];k[1][7]=q[8];


	printf("密钥序列为:");
	for(i=0;i<10;i++)printf("%d",key[i]);
	//GenerKey(key,k);
	printf("\nSubkey1:");
	for(j=0;j<8;j++)
		printf("%d ",k[0][j]);
	printf("\nSubkey2:");
	for(j=0;j<8;j++)
		printf("%d ",k[1][j]);
	if(m==1){
		printf("\n输入要加密的文件名:");
		getchar();
		scanf("%s",filename);
		if((fp=fopen(filename,"r"))==NULL)
			printf("error");
		len_plaint=fread(plaintext,sizeof(char),1000,fp);
		//将文件中的内容读到缓冲区里
		plaintext[len_plaint]='\0';
		printf("明文为:%s",plaintext);
	}	
	else if(m==2){
		printf("\n输入明文:");
		scanf("%s",plaintext);
		len_plaint=strlen(plaintext);
	}
	//将明文转换成二进制序列
	//binary_plaint=(int *)malloc(8*len_plaint*sizeof(int));
	binary_plaint=new int[8*len_plaint];
	for(i=0;i<len_plaint;i++)
		for(j=7+i*8;j>=i*8;j--)
		{binary_plaint[j]=plaintext[i]%2;plaintext[i]=plaintext[i]/2;}
	//对明文按DES加密步骤加密,每8位的进行操作
	for(i=0;i<8*len_plaint;i=i+8)
		DES(&binary_plaint[i],k);
	//将二进制转换成字符形式
	for(i=0;i<len_plaint;i++)
		ciphertext[i]=0;
	for(i=0;i<len_plaint;i++)
		for(j=i*8;j<8+i*8;j++)
			ciphertext[i]+=binary_plaint[j]*pow(z,(7-j%8));
	ciphertext[len_plaint]='\0';
	printf("加密结果为:%s\n",ciphertext);
}

void RDES(int *a,int **key){
	int q[8],p[8],i,j;
	q[0]=a[1];q[1]=a[5];q[2]=a[2];q[3]=a[0];
	q[4]=a[3];q[5]=a[7];q[6]=a[4];q[7]=a[6];
	for(i=1;i>=0;i--){
		for(j=0;j<8;j++)p[j]=q[j];
		FBox(p,key[i]);
		for(j=0;j<4;j++)q[j+4]=q[j];
		for(j=0;j<4;j++)q[j]=(p[j+4]+p[j])%2;
	}
	a[0]=q[3];a[1]=q[0];a[2]=q[2];a[3]=q[4];
	a[4]=q[6];a[5]=q[1];a[6]=q[7];a[7]=q[5];	
}

void Decrypht(){
	char plaintext[1000];
	char ciphertext[1000];
	float z=2;
	int key[10],numkey,i,j,**finalkey,len_ciphert,*binary_ciphert,m;
	finalkey=(int **)malloc(2*sizeof(int *));
	finalkey[0]=(int *)malloc(8*sizeof(int));
	finalkey[1]=(int *)malloc(8*sizeof(int));
	FILE *fp;char filename[30];
	printf("给文件解密输入1,直接解密输入2:");
	scanf("%d",&m);
	printf("输入一个0--1023的密钥:");
	scanf("%d",&numkey);
	for(i=9;i>=0;i--){key[i]=numkey%2;numkey=numkey/2;}
	printf("密钥序列为:");
	for(i=0;i<10;i++)printf("%d",key[i]);
	GenerKey(key,finalkey);
	printf("\nSubkey1:");
	for(j=0;j<8;j++)
		printf("%d ",finalkey[0][j]);
	printf("\nSubkey2:");
	for(j=0;j<8;j++)
		printf("%d ",finalkey[1][j]);
	if(m==1){
		printf("\n输入要加密的文件名:");
		getchar();
		scanf("%s",filename);
		if((fp=fopen(filename,"r"))==NULL)
			printf("error");
		len_ciphert=fread(ciphertext,sizeof(char),1000,fp);
		ciphertext[len_ciphert]='\0';
		printf("密文为:%s",ciphertext);
	}	
	else if(m==2){
		printf("\n输入密文:");
		scanf("%s",ciphertext);
		len_ciphert=strlen(ciphertext);
	}
	//将密文转换成二进制序列
	binary_ciphert=(int *)malloc(8*len_ciphert*sizeof(int));
	for(i=0;i<len_ciphert;i++)
		for(j=7+i*8;j>=i*8;j--)
		{binary_ciphert[j]=ciphertext[i]%2;ciphertext[i]=ciphertext[i]/2;}
	//对密文序列每8位的进行操作
	for(i=0;i<8*len_ciphert;i=i+8)
		RDES(&binary_ciphert[i],finalkey);
	//将二进制转换成字符形式
	for(i=0;i<len_ciphert;i++)
		plaintext[i]=0;
	for(i=0;i<len_ciphert;i++)
		for(j=i*8;j<8+i*8;j++)
			plaintext[i]+=binary_ciphert[j]*pow(z,(7-j%8));
	plaintext[len_ciphert]='\0';
	printf("明文为:%s\n",plaintext);
}

void main(){
	char c;
	while(1){
		printf("加密输入1,解密输入2,退出输入0:");
		scanf("%c",&c);
		if(c=='1')Encrypht();
		else if(c=='2')Decrypht();
		else if(c=='0')break;
	}
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -