网络空间安全概论 实验1加密 加密算法_第1页
网络空间安全概论 实验1加密 加密算法_第2页
网络空间安全概论 实验1加密 加密算法_第3页
网络空间安全概论 实验1加密 加密算法_第4页
网络空间安全概论 实验1加密 加密算法_第5页
已阅读5页,还剩26页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

目录1仿射密码 仿射密码算法简介仿射密码是一种替换密码,即一个字母对应一个字母。明文中的所有字母都在字母表上乘以系数,再向后(或向前)按照一个固定数目进行偏移后被替换成密文。明文记为m,密文记为c,密钥记为,加密变换记为E(m),解密变换记为D(m),n为基本字符的个数。它的加密函数是:,其中和n\t"/item/%E4%BB%BF%E5%B0%84%E5%AF%86%E7%A0%81/_blank"互素。解密函数是:,此处满足等式。核心代码辗转相除法求最大公约数(用于检验和n是否互素):求逆元(用于求):加密算法:解密算法:算法流程图:实验结果当输入与26不互素时,提示输入密钥不合法,如图1-1所示;图1-1输入密钥不合法时当输入密钥合法时,输入明文,程序给出相应加密后的密文,并将密文解密,如图1-2所示。图1-2输入密钥合法时进行加解密实验分析因为仿射密码仍为单字母表密码,其依旧保留了该类别加密之弱处。当=1时,仿射加密为恺撒(Caesar)密码,该加密方程可简化为线性移动;当=0时,仿射加密为乘数密码。考虑加密英文,即n=26,除去当=1且=0的情况,总共有26*12-1=311种非易仿射密钥对。因为密码缺少复杂性,根据\t"/item/%E4%BB%BF%E5%B0%84%E5%AF%86%E7%A0%81/_blank"柯克霍夫原则,这套系统是不安全的。此密码之首要弱处为,如果密码学家可发现(如\t"/item/%E4%BB%BF%E5%B0%84%E5%AF%86%E7%A0%81/_blank"频率分析,暴力破解,臆测或任何其他方法)加密文件两字元之原文,则关键值可透过解一\t"/item/%E4%BB%BF%E5%B0%84%E5%AF%86%E7%A0%81/_blank"方程组得到。2序列密码2.1算法简介线性反馈移位寄存器(linearfeedbackshiftregister,LFSR)是指,给定前一状态的输出,将该输出的\t"/item/%E7%BA%BF%E6%80%A7%E5%8F%8D%E9%A6%88%E7%A7%BB%E4%BD%8D%E5%AF%84%E5%AD%98%E5%99%A8/_blank"线性函数再用作输入的移位寄存器。异或运算是最常见的单比特线性函数:对寄存器的某些位进行异或操作后作为输入,再对寄存器中的各比特进行整体移位。影响下一个状态的比特位叫做抽头。LFSR最高位的比特为输出比特。抽头依次与输出比特进行异或运算,然后反馈回最低位。最高位所生成的序列被称为输出流。最大长度的LFSR生成一个m序列(例如,只有与有一定抽序列的LFSR才能通过所有2n−1个内部状态,不包括全零状态),除非它本身为全零,亦即状态永不改变。16位的本源多项式为,常数“1”并不代表某一个抽头,它所指的是一个比特位的输入。2.2核心代码将初始状态转换为二进制表示,其中again用于计算周期:生成序列:算法流程图:2.3实验结果当初始状态为18即0000000000010010时,输出序列周期为65535,如图2-1-1、2-1-2所示;图2-1-1初始状态为18时图2-1-2初始状态为18时的序列周期当初始状态为4569即0001000111011001时,输出序列周期为65535,如图2-2-1、2-2-2所示;图2-2-1初始状态为4569时图2-2-2初始状态为4569时的序列周期当初始状态为18即0000000000010010时,修改多项式为(非本原多项式),输出序列周期为63,如图2-3所示;图2-3非本原多项式,初始状态为18时2.4实验分析对于m序列(周期为2n-1),如果攻击者知道了2n位明密文对,则可确定反馈多项式的系数,从而确定该LFSR接下来的状态,也就能得到余下的密钥序列。由此可见,采用线性移位寄存器产生的序列密码在已知明文攻击下时可以破译的,所以,尽管m序列的随即性能良好且在所有同阶的线性移位寄存器生成序列中周期最长,但从序列密码安全角度来看,m序列不合适直接作为密钥序列来使用,也就是说,密钥序列产生器单有线性移位寄存器是不够的,还需要非线性组合部分。3DES加解密3.1算法简介DES算法全称为DataEncryptionStandard,即数据加密标准,是一种使用密钥加密的块算法,1977年被美国联邦政府的国家标准局确定为联邦资料处理标准(FIPS),并授权在非密级政府通信中使用,随后该算法在国际上广泛流传开来。DES是一个分组加密算法,典型的DES以64位为分组对数据加密,加密和解密用的是同一个算法。1、密钥长64位,密钥事实上是56位参与DES运算(第8、16、24、32、40、48、56、64位是校验位,使得每个密钥都有奇数个1),分组后的明文组和56位的密钥按位替代或交换的方法形成密文组。DES算法的主要流程如下图所示:2、IP置换IP置换目的是将输入的64位数据块按位重新组合,并把输出分为L0、R0两部分,每部分各长32位。置换规则如下表所示:58504234261810260524436282012462544638302214664564840322416857494133251791595143352719113615345372921135635547393123157表中的数字代表新数据中此位置的数据在原数据中的位置,即原数据块的第58位放到新数据的第1位,第50位放到第2位,……依此类推,第7位放到第64位。置换后的数据分为L0和R0两部分,L0为新数据的左32位,R0为新数据的右32位。要注意一点,位数是从左边开始数的,即最0x0000008000000002最左边的位为1,最右边的位为64。3、密钥置换不考虑每个字节的第8位,DES的密钥由64位减至56位,每个字节的第8位作为奇偶校验位。产生的56位密钥由下表生成(注意表中没有8,16,24,32,40,48,56和64这8位):57494133251791585042342618102595343252719113605244366355473931231576254463830221466153453729211352820124在DES的每一轮中,从56位密钥产生出不同的48位子密钥,确定这些子密钥的方式如下:(1)将56位的密钥分成两部分,每部分28位。(2)根据轮数,这两部分分别循环左移1位或2位。每轮移动的位数如下表:轮数12345678910111213141516位数1122222212222221移动后,从56位中选出48位。这个过程中,既置换了每位的顺序,又选择了子密钥,因此称为压缩置换。4、E扩展置换扩展置置换目标是IP置换后获得的右半部分R0,将32位输入扩展为48位(分为4位×8组)输出。扩展置换目的有两个:生成与密钥相同长度的数据以进行异或运算;提供更长的结果,在后续的替代运算中可以进行压缩。扩展置换原理如下表:3212345456789891011121312131415161716171819202120212223242524252627282928293031321表中的数字代表位,两列黄色数据是扩展的数据,可以看出,扩展的数据是从相邻两组分别取靠近的一位,4位变为6位。靠近32位的位为1,靠近1位的位为32。表中第二行的4取自上组中的末位,9取自下组中的首位。我们举个例子看一下(虽然扩展置换针对的是上步IP置换中的R0,但为便于观察扩展,这里不取R0举例):输入数据0x10811001,转换为二进制就是0001000010000001B,按照上表扩展得下表:100010100001010000000010100010100000000000000010表中的黄色数据是从临近的上下组取得的,二进制为100010100001010000000010100010100000000000000010B,转换为十六进制0x8A14028A0002。扩展置换之后,右半部分数据R0变为48位,与密钥置换得到的轮密钥进行异或。5、S盒代替压缩后的密钥与扩展分组异或以后得到48位的数据,将这个数据送人S盒,进行替代运算。替代由8个不同的S盒完成,每个S盒有6位输入4位输出。48位输入分为8个6位的分组,一个分组对应一个S盒,对应的S盒对各组进行代替操作。一个S盒就是一个4行16列的表,盒中的每一项都是一个4位的数。S盒的6个输入确定了其对应的输出在哪一行哪一列,输入的高低两位做为行数H,中间四位做为列数L,在S-BOX中查找第H行L列对应的数据(<32)。一共8个S盒代替过程产生8个4位的分组,组合在一起形成32位数据。S盒代替时DES算法的关键步骤,所有的其他的运算都是线性的,易于分析,而S盒是非线性的,相比于其他步骤,提供了更好安全性。6、P盒置换S盒代替运算的32位输出按照P盒进行置换。该置换把输入的每位映射到输出位,任何一位不能被映射两次,也不能被略去,映射规则如下表:1672021291228171152326518311028241432273919133062211425表中的数字代表原数据中此位置的数据在新数据中的位置,即原数据块的第16位放到新数据的第1位,第7位放到第2位,……依此类推,第25位放到第32位。例如0x10A10001进行P盒置换后变为0x80000886。0x10A10001表现为表的形式(第一位位于左上角)原来为:00010000101000010000000000000001经P盒变换后为:10000000000000000000100010000110即10000000000000000000100010000110B,十六进制为0x80000886.最后,P盒置换的结果与最初的64位分组左半部分L0异或,然后左、右半部分交换,接着开始另一轮。7、IP-1末置换末置换是初始置换的逆过程,DES最后一轮后,左、右两半部分并未进行交换,而是两部分合并形成一个分组做为末置换的输入。末置换规则如下表:40848165624643239747155523633138646145422623037545135321612936444125220602835343115119592734242105018582633141949175725置换方法同上,此处省略。经过以上步骤,就可以得到密文了。3.2核心代码将默认值输入:对56位密钥的前后部分进行左移:生成16个48位的子密钥:将char字符数组转为二进制:扩展置换,32->48:异或、查找S_BOX置换表:P置换,32->32:加密过程:解密过程:3.3实验结果百度找到的测试结果:plaintextkeyciphertext0756D8E0774761D20170F175468FB5E60CD3DA020021DC09进行检验,结果一致:3.5实验分析最初的罗斯福密码中密钥长度为128位,DES的加密单位仅有64位二进制,而且其中某些位还要用于奇偶校验或其他通讯开销,有效密码只有56位,这对于数据传输来说太小,各次迭代中使用的密钥是递推产生的,这种相关性必然降低了密码体制的安全性。至今,最有效的破解方法是穷举搜索法,那么56位长的密钥总共要测试256次,花费时间太长。近年来有人提出用差分和线性攻击方案来破解DES算法,虽然,从理论上来说破译的性能高于穷举搜索法,但要有超高速计算机提供支持。尽管如此,我们仍然需要考虑对DES算法进行改进,使密钥长度增加些,以实现更好的保密功能。针对DES算法上的缺陷,各国专家们都在研究如何增强DES算法的安全性,现在已发展出几十种改进的DES,经过比较,笔者认为多重DES具有较高的可行性。为了增加密钥的长度,采用多重DES加密技术,将分组密码进行级联,在不同的密钥作用下,连续多次对一组明文进行加密。针对DES算法,专家们的共识是采用三重DES加密算法。在DES算法中存在12个半弱密钥和4个弱密钥。应避免出现这16种弱密钥。附件:附件1.仿射密码主要代码#include<iostream>#include<string.h>usingnamespacestd;charm[100];charc[100];intgcd(inta,intb)//辗转相除法求a,b的最大公约数{ intk=0; do { k=a%b; a=b; b=k; }while(k!=0); returna;}intInverse(inta,intb)//求a相对b的逆元{ inti=0; while(a*(++i)%b!=1);//a*i=1(modb) returni;}voidEncryption(charm[],intk1,intk2)//加密{ intlen=strlen(m); for(inti=0;i<len;i++) { c[i]=(k1*(m[i]-97)+k2)%26+65;//加密公式c=e(m)=k1*m+k2(mod26) } cout<<"加密后的密文为:"; for(inti=0;i<len;i++) cout<<c[i]; cout<<endl;}voidDecryption(charc[],intk1,intk2)//解密{ intlen=strlen(c); charm1[100]; for(inti=0;i<len;i++) { intt=c[i]-65-k2; if(t<0) { t=t+26; } m1[i]=k1*t%26+97;//解密公式m=(e(m)-k2)*(k1^-1)(mod26) } cout<<"解密后的明文为:"; for(inti=0;i<len;i++) cout<<m1[i]; cout<<endl;}intmain(){ intk1,k2; cout<<"请输入密钥k1、k2:"; cin>>k1>>k2; while(gcd(k1,26)!=1)//判断输入的密钥是否合法 { cout<<"输入的密钥不合法,请重新输入k1、k2:"<<endl; cin>>k1>>k2; } cout<<"请输入需要加密的明文:"; cin>>m; Encryption(m,k1,k2); intk3=Inverse(k1,26); cout<<"解密密钥为:"; cout<<k3<<""<<k2<<endl; Decryption(c,k3,k2); return0;}附件2.序列密码主要代码#include<bits/stdc++.h>typedeflonglongll;#definen16usingnamespacestd;intmain(){ bitset<n>bint(18); bitset<n>str(bint); strings1,s2; llagain=0;//序列周期 cout<<"初始状态为:"<<bint.to_string()<<endl; do { intj=bint[15]^bint[4]^bint[2]^bint[0];//本原多项式为:x^16+x^5+x^3+x+1 s1=bint.to_string(); s2.push_back(s1[n-1]); bint.operator>>=(1); bint[n-1]=j; again++; }while(str.to_string()!=bint.to_string()); cout<<endl; cout<<"输出序列为:"<<s2<<endl; cout<<"序列周期为:"<<again<<endl; return0;}附件3.DES加解密主要代码#include<bits/stdc++.h>usingnamespacestd;bitset<64>key;//64位密钥bitset<48>subKey[16];//存放16轮子密钥//初始置换表intIP[]={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, 59,51,43,35,27,19,11,3, 61,53,45,37,29,21,13,5, 63,55,47,39,31,23,15,7};//结尾置换表intIP_1[]={40,8,48,16,56,24,64,32, 39,7,47,15,55,23,63,31, 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};//密钥置换表,将64位密钥变成56位intPC_1[]={57,49,41,33,25,17,9, 1,58,50,42,34,26,18, 10,2,59,51,43,35,27, 19,11,3,60,52,44,36, 63,55,47,39,31,23,15, 7,62,54,46,38,30,22, 14,6,61,53,45,37,29, 21,13,5,28,20,12,4};//压缩置换,将56位密钥压缩成48位子密钥intPC_2[]={14,17,11,24,1,5, 3,28,15,6,21,10, 23,19,12,4,26,8, 16,7,27,20,13,2, 41,52,31,37,47,55, 30,40,51,45,33,48, 44,49,39,56,34,53, 46,42,50,36,29,32};//每轮左移的位数intshiftBits[]={1,1,2,2,2,2,2,2,1,2,2,2,2,2,2,1};//扩展置换表,将32位扩展至48位intE[]={32,1,2,3,4,5, 4,5,6,7,8,9, 8,9,10,11,12,13, 12,13,14,15,16,17, 16,17,18,19,20,21, 20,21,22,23,24,25, 24,25,26,27,28,29, 28,29,30,31,32,1};//S盒,每个S盒是4x16的置换表,6位->4位intS_BOX[8][4][16]={ { {14,4,13,1,2,15,11,8,3,10,6,12,5,9,0,7}, {0,15,7,4,14,2,13,1,10,6,12,11,9,5,3,8}, {4,1,14,8,13,6,2,11,15,12,9,7,3,10,5,0}, {15,12,8,2,4,9,1,7,5,11,3,14,10,0,6,13} }, { {15,1,8,14,6,11,3,4,9,7,2,13,12,0,5,10}, {3,13,4,7,15,2,8,14,12,0,1,10,6,9,11,5}, {0,14,7,11,10,4,13,1,5,8,12,6,9,3,2,15}, {13,8,10,1,3,15,4,2,11,6,7,12,0,5,14,9} }, { {10,0,9,14,6,3,15,5,1,13,12,7,11,4,2,8}, {13,7,0,9,3,4,6,10,2,8,5,14,12,11,15,1}, {13,6,4,9,8,15,3,0,11,1,2,12,5,10,14,7}, {1,10,13,0,6,9,8,7,4,15,14,3,11,5,2,12} }, { {7,13,14,3,0,6,9,10,1,2,8,5,11,12,4,15}, {13,8,11,5,6,15,0,3,4,7,2,12,1,10,14,9}, {10,6,9,0,12,11,7,13,15,1,3,14,5,2,8,4}, {3,15,0,6,10,1,13,8,9,4,5,11,12,7,2,14} }, { {2,12,4,1,7,10,11,6,8,5,3,15,13,0,14,9}, {14,11,2,12,4,7,13,1,5,0,15,10,3,9,8,6}, {4,2,1,11,10,13,7,8,15,9,12,5,6,3,0,14}, {11,8,12,7,1,14,2,13,6,15,0,9,10,4,5,3} }, { {12,1,10,15,9,2,6,8,0,13,3,4,14,7,5,11}, {10,15,4,2,7,12,9,5,6,1,13,14,0,11,3,8}, {9,14,15,5,2,8,12,3,7,0,4,10,1,13,11,6}, {4,3,2,12,9,5,15,10,11,14,1,7,6,0,8,13} }, { {4,11,2,14,15,0,8,13,3,12,9,7,5,10,6,1}, {13,0,11,7,4,9,1,10,14,3,5,12,2,15,8,6}, {1,4,11,13,12,3,7,14,10,15,6,8,0,5,9,2}, {6,11,13,8,1,4,10,7,9,5,0,15,14,2,3,12} }, { {13,2,8,4,6,15,11,1,10,9,3,14,5,0,12,7}, {1,15,13,8,10,3,7,4,12,5,6,11,0,14,9,2}, {7,11,4,1,9,12,14,2,0,6,10,13,15,3,5,8}, {2,1,14,7,4,10,8,13,15,12,9,0,3,5,6,11} }};//P置换,32位->32位intP[]={16,7,20,21, 29,12,28,17, 1,15,23,26, 5,18,31,10, 2,8,24,14, 32,27,3,9, 19,13,30,6, 22,11,4,25};bitset<32>f(bitset<32>R,bitset<48>k){ bitset<48>expandR; //第一步:扩展置换,32->48 for(inti=0;i<48;++i) expandR[47-i]=R[32-E[i]]; //第二步:异或 expandR=expandR^k; //第三步:查找S_BOX置换表 bitset<32>output; intx=0; for(inti=0;i<48;i=i+6) { introw=expandR[47-i]*2+expandR[47-i-5]; intcol=expandR[47-i-1]*8+expandR[47-i-2]*4+expandR[47-i-3]*2+expandR[47-i-4]; intnum=S_BOX[i/6][row][col]; bitset<4>binary(num); output[31-x]=binary[3]; output[31-x-1]=binary[2]; output[31-x-2]=binary[1]; output[31-x-3]=binary[0]; x+=4; } //第四步:P-置换,32->32 bitset<32>tmp=output; for(inti=0;i<32;++i) output[31-i]=tmp[32-P[i]]; returnoutput;}/***对56位密钥的前后部分进行左移*/bitset<28>leftShift(bitset<28>k,intshift){ bitset<28>tmp=k; for(inti=27;i>=0;--i) { if(i-shift<0) k[i]=tmp[i-shift+28]; else k[i]=tmp[i-shift]; } returnk;}/***生成16个48位的子密钥*/voidgenerateKeys(){ bitset<56>realKey; bitset<28>left; bitset<28>right; bitset<48>compressKey; //去掉奇偶标记位,将64位密钥变成56位 for(inti=0;i<56;++i) realKey[55-i]=key[64-PC_1[i]]; //生成子密钥,保存在subKeys[16]中 for(intround=0;round<16;++round) { //前28位与后28位 for(inti=28;i<56;++i) left[i-28]=realKey[i]; for(inti=0;i<28;++i) right[i]=realKey[i]; //左移 left=leftShift(left,shiftBits[round]); right=leftShift(right,shiftBits[round]); //压缩置换,由56位得到48位子密钥 for(inti=28;i<56;++i) realKey[i]=left[i-28]; for(inti=0;i<28;++i) realKey[i]=right[i]; for(inti=0;i<48;++i) compressKey[47-i]=realKey[56-PC_2[i]]; subKey[round]=compressKey; }}/***工具函数:将char字符数组转为二进制*/bitset<64>charToBitset(constchars[8]){ bitset<64>bits; for(inti=0;i<8;++i) for(intj=0;j<8;++j) bits[i*8+j]=((s[i]>>j)&1); returnbits;}/***DES加密*/bitset<64>encrypt(bitset<64>&plain){ bitset<64>cipher; bitset<64>currentBits; bitset<32>left; bitset<32>right; bitset<32>newLeft; //第一步:初始置换IP for(inti=0;i<64;++i) currentBits[63-i]=plain[64-IP[i]]; //第二步:获取Li和Ri for(inti=32;i<64;++i) left[i-32]=currentBits[i]; for(inti=0;i<32;++i) right[i]=currentBits[i]; //第三步:共16轮迭代 for(intround=0;round<16;++round) { newLeft=right; right=left^f(right,subKey[round]); left=newLeft; } //第四步:合并L16和R16,注意合并为R16L16 for(inti=0;i<32;++i) cipher[i]=left[i]; for(inti=32;i<64;++i) cipher[i]=right[i-32]; //第五步:结尾置换IP-1 currentBits=cipher; for(inti=0;i<64;++i) cipher[63-i]=currentBits[64-IP_1[i]]; //返回密文 returncipher;}/***DES解密*/bitset<64>decrypt

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论