密码学实验三—DES算法的实现课案
合集下载
相关主题
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
【参数使用】
char* msg;
char *key;
【实验结果】
实验数据:
六、参考资料(书籍或网络文章)
《密码编码学与网络安全——原理与实践(第五版)》
百度
七、实验心得和总结
做这次DES加解密实验前首先要充分了解其原理,在这个实验中,比较难的就是,要将明文和密钥经过初始变换和十六轮加密变换等一系列变换后才能得到置换,其中的变换步骤比较多,而且比较复杂,还要将十六进制转化为二进制,工作量比较大。
voidDES::InitSwap(boolin[64])
{
//打乱
for(inti = 0; i < 32; i++)
{
lmsgi[i] =in[ip[i] - 1];
rmsgi[i] =in[ip[i + 32] - 1];
}
};
//
//初始逆置换函数
voidDES::InitReSwap(boolout[64])
{
//组合成64数组
booltemp[64];
for(inti = 0; i < 32; i++)
{
temp[i] = rmsgi[i];
temp[32 + i] = lmsgi[i];
}
//按照逆ip矩阵
for(inti = 0; i < 64; i++)
{
out[i] = temp[back_ip[i] - 1];
}
};
//
voidDES::SubKeyOff(bool*_subkey,int_off)
{
booltemp;
for(inti = 0; i <_off; i++)
{
temp =_subkey[0];
for(inti = 0; i < 27; i++)
{
_subkey[i] =_subkey[i + 1];
2.将输入的第58位换到第一位,第50位换到第2位,...,依此类推,最后一位是原来的第7位。L0、R0则是换位输出后的两部分,L0是输出的左32位,R0是右32位,例:设置换前的输入值为D1D2D3......D64,则经过初始置换后的结果为:L0=D550...D8;R0=D57D49...D7。
{
//e操作
booltemp1[48];
EOperation(in, temp1);
booltemp2[48];
Mode2Add(temp1, (bool*)subkey[isubkey], temp2, 48);//ok
//盒子压缩
booltemp3[48];
DealSBox(temp2, temp3);
58,50,12,34,26,18,10,2,60,52,44,36,28,20,12,4,
62,54,46,38,30,22,14,6,64,56,48,40,32,24,16,8,
57,49,41,33,25,17, 9,1,59,51,43,35,27,19,11,3,
61,53,45,37,29,21,13,5,63,55,47,39,31,23,15,7,
经过26次迭代运算后。得到L16、R16,将此作为输入,进行逆置换,即得到密文输出。逆置换正好是初始置的逆运算,例如,第1位经过初始置换后,处于第40位,而通过逆置换,又将第40位换回到第1位,其逆置换规则如下表所示:
40,8,48,16,56,24,64,32,39,7,47,15,55,23,63,31,
//总的的加密流程
voidCrypte();
//解密
voidDecipher();
//输出密文
voidOutPutCryptedMsg();
//二进制转成字符
voidBit2Char(bool* _barray,char* _carray);//length=64
//输出解密后的明文
voidOutPutDecipher();
//模2相加
//相同为0不同为1
voidMode2Add(boola[],boolb[],boolc[],intlength);
//sbox
voidDealSBox(boolin[48],boolout[32]);
void_DealSBox(boolin[6],boolout[4],intbox);
59,51,43,35,27,19,11,3,
61,53,45,37,29,21,13,5,
63,55,47,39,31,23,15,7
};
constintDES::c0[28] = {
57,49,41,33,25,17,9,
1,58,50,42,34,26,18,
10,2,59,51,43,35,27,
}
else
{
//L2=R1
CopyArray(rmsgi1, lmsgi, 32);
//f(R1,k1)
CrypteFunction(rmsgi1, 15 - i, temp1);
//L1+f(R1,k1)
Mode2Add(lmsgi1, temp1, temp2, 32);
//R2=L1+f(R1,k1)
private:
//字符转成二进制,并保存到64位bool数组中
voidChar2Bit(char* _carray,bool* _barray,intlength);
////二进制转成字符
//void Bit2Char(bool* _barray,char* _carray);//length=64
19,11,3,60,52,44,36
};
constintDES::d0[28] = {
}
_subkey[27] = temp;
}
};
4.S盒处理:
voidDES::DealSBox(boolin[48],boolout[32])
{
bool_in[6], _out[4];
//8个盒子
for(inti = 0; i < 8; i++)
{
//提取盒子
for(intj = 0; j < 6; j++)
{
_in[j] =in[i * 6 + j];
}
//压缩
_DealSBox(_in, _out, i);
//放进out数组
for(intjj = 0; jj < 4; jj++)
{
out[i * 4 + jj] = _out[jj];
}
}
};
5.加密函数:
voidDES::CrypteFunction(boolin[32],intisubkey,boolout[32])
//p opraration
voidPOperation(booltemp[32],boolresult[32]);
//加密函数
voidCrypteFunction(boolin[32],intisubkey,boolout[32]);
//数组之间赋值
voidCopyArray(boolarray1[],boolarray2[],intsize);
boolbdecipher[64];
chardecipher[8];
private:
//静态常量
//不允许在类内初始化
//初始值换ip
conststaticintip[64];
//子密钥
//置换选择1
conststatiwenku.baidu.comintc0[28];
conststaticintd0[28];
//循环左移表
conststaticintkeyoff[16];
//16个子密钥
boolsubkey[16][48];
//l0 r0中间变量
boolrmsgi[32], lmsgi[32];//第i个
boolrmsgi1[32], lmsgi1[32];//第i+1个
//密文
boolbcryptedmsg[64];
charcryptedmsg[8];
//解密的结果
附:程序源代码
#include"stdafx.h"
#include<iostream>
#include<string.h>
usingnamespacestd;
classDES
{
private:
//明文
charmsg[8];
boolbmsg[64];
//密钥
charkey[8];
boolbkey[64];
CopyArray(temp2, rmsgi, 32);
}
}
//逆初始置换ip
InitReSwap(bdecipher);
//转成字符
Bit2Char(bdecipher, decipher);
};
四、
【开发环境】
Microsoft Visual Studio 2015
Microsoft Windows 10
};
2.输入密钥:
voidDES::SetKey(char*_key,int_length)
{
if(_length>8)
{
return;
}
for(inti = 0; i <_length; i++)
{
key[i] =_key[i];
}
//转成二进制
Char2Bit(key, bkey, 8);
};
3.各种置换:
//置换选择2
conststaticintdi[48];
//加密函数
//e运算
conststaticinte_operate[48];
//sbox
conststaticintsbox[8][64];
//置换运算p
conststaticintp_operate[32];
//逆初始置换ip
conststaticintback_ip[64];
//置换运算p
POperation(temp3,out);
};
6.解密函数:
voidDES::Decipher()
{
booltemp1[32], temp2[32];
//初始置换ip
InitSwap(bcryptedmsg);
//16轮迭代加密
for(inti = 0; i < 16; i++)
{
if(i % 2 == 0)
38,6,46,14,54,22,62,30,37,5,45,13,53,21,61,29,
36,4,44,12,52,20,60,28,35,3,43,11,51,19,59,27,
34,2,42,10,50,18,58 26,33,1,41, 9,49,17,57,25,
3.DES算法的解密过程是一样的,区别仅仅在於第一次迭代时用子密钥K15,第二次K14、......,最后一次用K0,算法本身并没有变化。
实验三用DES实现对数据的加解密
一、实验目的
1.用DES加密方法实现对明文的加密
2.用DES解密加密后的密文
二、实验内容
1、给定八字节明文,输入8位密钥对明文加密
2、用同一个密钥对加密的密文解密的到原来的明文
三、实验原理
实验步骤(包括流程图、功能模块)
【实验原理】
1、DES算法把64位的明文输入块变为64位的密文输出块,它所使用的密钥也是64位,其功能是把输入的64位数据块按位重新组合,并把输出分为L0、R0两部分,每部分各长32位,其置换规则见下表:
};
usingnamespacestd;
//静态常量
constintDES::ip[64] = {
58,50,42,34,26,18,10,2,
60,52,44,36,28,20,12,4,
62,54,46,38,30,22,14,6,
64,56,48,40,32,24,16,8,
57,49,41,33,25,17,9,1,
{
//L1=R0
CopyArray(rmsgi, lmsgi1, 32);
//f(R0,k0)
CrypteFunction(rmsgi, 15 - i, temp1);
//L0+f(R0,k0)
Mode2Add(lmsgi, temp1, temp2, 32);
//R1=L0+f(R0,k0)
CopyArray(temp2, rmsgi1, 32);
//位掩码
conststaticcharbitmask[8];
public:
//设置明文和密钥
//_length要小于或等于8
voidSetMsg(char* _msg,int_length);
voidSetKey(char* _msg,int_length);
//生产子密钥
voidProduceSubKey();
//初始置换
voidInitSwap(boolin[64]);
//初始逆置换
voidInitReSwap(boolout[64]);
//循环左移
voidSubKeyOff(bool* _subkey,int_off);
//e运算操作函数
voidEOperation(boola[32],boolb[48]);
【算法流程图】
【功能模块】
1.输入明文:
voidDES::SetMsg(char*_msg,int_length)
{
if(_length>8)
{
return;
}
for(inti = 0; i <_length; i++)
{
msg[i] =_msg[i];
}
//转换成二进制
Char2Bit(msg, bmsg, 8);
char* msg;
char *key;
【实验结果】
实验数据:
六、参考资料(书籍或网络文章)
《密码编码学与网络安全——原理与实践(第五版)》
百度
七、实验心得和总结
做这次DES加解密实验前首先要充分了解其原理,在这个实验中,比较难的就是,要将明文和密钥经过初始变换和十六轮加密变换等一系列变换后才能得到置换,其中的变换步骤比较多,而且比较复杂,还要将十六进制转化为二进制,工作量比较大。
voidDES::InitSwap(boolin[64])
{
//打乱
for(inti = 0; i < 32; i++)
{
lmsgi[i] =in[ip[i] - 1];
rmsgi[i] =in[ip[i + 32] - 1];
}
};
//
//初始逆置换函数
voidDES::InitReSwap(boolout[64])
{
//组合成64数组
booltemp[64];
for(inti = 0; i < 32; i++)
{
temp[i] = rmsgi[i];
temp[32 + i] = lmsgi[i];
}
//按照逆ip矩阵
for(inti = 0; i < 64; i++)
{
out[i] = temp[back_ip[i] - 1];
}
};
//
voidDES::SubKeyOff(bool*_subkey,int_off)
{
booltemp;
for(inti = 0; i <_off; i++)
{
temp =_subkey[0];
for(inti = 0; i < 27; i++)
{
_subkey[i] =_subkey[i + 1];
2.将输入的第58位换到第一位,第50位换到第2位,...,依此类推,最后一位是原来的第7位。L0、R0则是换位输出后的两部分,L0是输出的左32位,R0是右32位,例:设置换前的输入值为D1D2D3......D64,则经过初始置换后的结果为:L0=D550...D8;R0=D57D49...D7。
{
//e操作
booltemp1[48];
EOperation(in, temp1);
booltemp2[48];
Mode2Add(temp1, (bool*)subkey[isubkey], temp2, 48);//ok
//盒子压缩
booltemp3[48];
DealSBox(temp2, temp3);
58,50,12,34,26,18,10,2,60,52,44,36,28,20,12,4,
62,54,46,38,30,22,14,6,64,56,48,40,32,24,16,8,
57,49,41,33,25,17, 9,1,59,51,43,35,27,19,11,3,
61,53,45,37,29,21,13,5,63,55,47,39,31,23,15,7,
经过26次迭代运算后。得到L16、R16,将此作为输入,进行逆置换,即得到密文输出。逆置换正好是初始置的逆运算,例如,第1位经过初始置换后,处于第40位,而通过逆置换,又将第40位换回到第1位,其逆置换规则如下表所示:
40,8,48,16,56,24,64,32,39,7,47,15,55,23,63,31,
//总的的加密流程
voidCrypte();
//解密
voidDecipher();
//输出密文
voidOutPutCryptedMsg();
//二进制转成字符
voidBit2Char(bool* _barray,char* _carray);//length=64
//输出解密后的明文
voidOutPutDecipher();
//模2相加
//相同为0不同为1
voidMode2Add(boola[],boolb[],boolc[],intlength);
//sbox
voidDealSBox(boolin[48],boolout[32]);
void_DealSBox(boolin[6],boolout[4],intbox);
59,51,43,35,27,19,11,3,
61,53,45,37,29,21,13,5,
63,55,47,39,31,23,15,7
};
constintDES::c0[28] = {
57,49,41,33,25,17,9,
1,58,50,42,34,26,18,
10,2,59,51,43,35,27,
}
else
{
//L2=R1
CopyArray(rmsgi1, lmsgi, 32);
//f(R1,k1)
CrypteFunction(rmsgi1, 15 - i, temp1);
//L1+f(R1,k1)
Mode2Add(lmsgi1, temp1, temp2, 32);
//R2=L1+f(R1,k1)
private:
//字符转成二进制,并保存到64位bool数组中
voidChar2Bit(char* _carray,bool* _barray,intlength);
////二进制转成字符
//void Bit2Char(bool* _barray,char* _carray);//length=64
19,11,3,60,52,44,36
};
constintDES::d0[28] = {
}
_subkey[27] = temp;
}
};
4.S盒处理:
voidDES::DealSBox(boolin[48],boolout[32])
{
bool_in[6], _out[4];
//8个盒子
for(inti = 0; i < 8; i++)
{
//提取盒子
for(intj = 0; j < 6; j++)
{
_in[j] =in[i * 6 + j];
}
//压缩
_DealSBox(_in, _out, i);
//放进out数组
for(intjj = 0; jj < 4; jj++)
{
out[i * 4 + jj] = _out[jj];
}
}
};
5.加密函数:
voidDES::CrypteFunction(boolin[32],intisubkey,boolout[32])
//p opraration
voidPOperation(booltemp[32],boolresult[32]);
//加密函数
voidCrypteFunction(boolin[32],intisubkey,boolout[32]);
//数组之间赋值
voidCopyArray(boolarray1[],boolarray2[],intsize);
boolbdecipher[64];
chardecipher[8];
private:
//静态常量
//不允许在类内初始化
//初始值换ip
conststaticintip[64];
//子密钥
//置换选择1
conststatiwenku.baidu.comintc0[28];
conststaticintd0[28];
//循环左移表
conststaticintkeyoff[16];
//16个子密钥
boolsubkey[16][48];
//l0 r0中间变量
boolrmsgi[32], lmsgi[32];//第i个
boolrmsgi1[32], lmsgi1[32];//第i+1个
//密文
boolbcryptedmsg[64];
charcryptedmsg[8];
//解密的结果
附:程序源代码
#include"stdafx.h"
#include<iostream>
#include<string.h>
usingnamespacestd;
classDES
{
private:
//明文
charmsg[8];
boolbmsg[64];
//密钥
charkey[8];
boolbkey[64];
CopyArray(temp2, rmsgi, 32);
}
}
//逆初始置换ip
InitReSwap(bdecipher);
//转成字符
Bit2Char(bdecipher, decipher);
};
四、
【开发环境】
Microsoft Visual Studio 2015
Microsoft Windows 10
};
2.输入密钥:
voidDES::SetKey(char*_key,int_length)
{
if(_length>8)
{
return;
}
for(inti = 0; i <_length; i++)
{
key[i] =_key[i];
}
//转成二进制
Char2Bit(key, bkey, 8);
};
3.各种置换:
//置换选择2
conststaticintdi[48];
//加密函数
//e运算
conststaticinte_operate[48];
//sbox
conststaticintsbox[8][64];
//置换运算p
conststaticintp_operate[32];
//逆初始置换ip
conststaticintback_ip[64];
//置换运算p
POperation(temp3,out);
};
6.解密函数:
voidDES::Decipher()
{
booltemp1[32], temp2[32];
//初始置换ip
InitSwap(bcryptedmsg);
//16轮迭代加密
for(inti = 0; i < 16; i++)
{
if(i % 2 == 0)
38,6,46,14,54,22,62,30,37,5,45,13,53,21,61,29,
36,4,44,12,52,20,60,28,35,3,43,11,51,19,59,27,
34,2,42,10,50,18,58 26,33,1,41, 9,49,17,57,25,
3.DES算法的解密过程是一样的,区别仅仅在於第一次迭代时用子密钥K15,第二次K14、......,最后一次用K0,算法本身并没有变化。
实验三用DES实现对数据的加解密
一、实验目的
1.用DES加密方法实现对明文的加密
2.用DES解密加密后的密文
二、实验内容
1、给定八字节明文,输入8位密钥对明文加密
2、用同一个密钥对加密的密文解密的到原来的明文
三、实验原理
实验步骤(包括流程图、功能模块)
【实验原理】
1、DES算法把64位的明文输入块变为64位的密文输出块,它所使用的密钥也是64位,其功能是把输入的64位数据块按位重新组合,并把输出分为L0、R0两部分,每部分各长32位,其置换规则见下表:
};
usingnamespacestd;
//静态常量
constintDES::ip[64] = {
58,50,42,34,26,18,10,2,
60,52,44,36,28,20,12,4,
62,54,46,38,30,22,14,6,
64,56,48,40,32,24,16,8,
57,49,41,33,25,17,9,1,
{
//L1=R0
CopyArray(rmsgi, lmsgi1, 32);
//f(R0,k0)
CrypteFunction(rmsgi, 15 - i, temp1);
//L0+f(R0,k0)
Mode2Add(lmsgi, temp1, temp2, 32);
//R1=L0+f(R0,k0)
CopyArray(temp2, rmsgi1, 32);
//位掩码
conststaticcharbitmask[8];
public:
//设置明文和密钥
//_length要小于或等于8
voidSetMsg(char* _msg,int_length);
voidSetKey(char* _msg,int_length);
//生产子密钥
voidProduceSubKey();
//初始置换
voidInitSwap(boolin[64]);
//初始逆置换
voidInitReSwap(boolout[64]);
//循环左移
voidSubKeyOff(bool* _subkey,int_off);
//e运算操作函数
voidEOperation(boola[32],boolb[48]);
【算法流程图】
【功能模块】
1.输入明文:
voidDES::SetMsg(char*_msg,int_length)
{
if(_length>8)
{
return;
}
for(inti = 0; i <_length; i++)
{
msg[i] =_msg[i];
}
//转换成二进制
Char2Bit(msg, bmsg, 8);