栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > C/C++/C#

DES算法C语言实现

C/C++/C# 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

DES算法C语言实现

有关DES的加密流程详解des算法加密流程_lkw23333的博客-CSDN博客_des密钥加密过程

此处只做简略介绍,或者看代码注释

简要流程

(1)输入8位字符明文以及设定8位字符的加密密钥;

(2)将字符串的明文转换为64位的二进制表示;密钥也转换为64位二进制表示;

(3)对64位的密钥进行密钥扩展生16个48位的子密钥;

(4)对64位明文进行ip置换,分成L与R两组各32位;

(5)R经过轮函数F后与L进行异或操作生成新的R,新的L由之前的R代替;

(6)重复上述步骤16次后再进行一次IP逆置换即可得到64位密文;

(7)将加密后64位密文转为16位16进制输出方便显示;

(8)解密与加密步骤相同只是部分操作相反;

总结

整个des算法涉及到的那种晦涩的理论知识并不多所以理解起来很容易。各种操作通过代码实现起来都很ez,理解起来也很ez。就是过程稍微有点繁杂,而且在写代码的过程中不能调试,只能写完了调,这就导致找bug有点痛苦。不过这个过程是有收获的。

#include
#include


int IP_Table[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,59,51,43,35,27,19,11, 3,
 61,53,45,37,29,21,13, 5,63,55,47,39,31,23,15, 7
};
// IP-1置换表
int IPR_Table[64]={
 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
};

// E扩展表
int E_Table[48]={
 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
};
// PC1置换表
int PC1_Table[56]={
 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
};

// pc2表
int PC2_Table[48]={
  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
};
//  移位表
int LOOP_Table[16]={
  1, 1, 2, 2, 2, 2, 2, 2, 1, 2, 2, 2, 2, 2, 2, 1
};
 // S盒
int S_Box[8][4][16]={
 //S1
 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,
 //S2
 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,
 //S3
 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,
 //S4
  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,
 //S5
  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,
 //S6
 12, 1,10,15, 9, 2, 6, 8, 0,13, 3, 4,14, 7, 5,11,
 10,15, 4, 2, 7,12, 0, 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,
 //S7
  4,11, 2,14,15, 0, 8,13, 3,12, 9, 7, 5,10, 6, 1,
 13, 0,11, 7, 4, 0, 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,
 //S8
 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置换表
int P_Table[32]={
 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
};

//执行des加密
void doDes(int *mingBit, char *ciphertext, int *keyBit);
//拷贝数组
void bitCopy(int *input, int *output, int length);
//做ip置换和逆置换
void doIp(int *array, int length, int *table);
//异或运算
void doXor(int *output, int *input, int length);
//E盒扩展
void doE(int *R, int *eTemp, int length);
//S盒压缩
void doS(int *R, int *eTemp);
//P盒置换
void doP(int *array);
//两个PC表的置换
void doPc_1(int *keyBit, int *output);
void doPc_2(int *iKey, int *C, int *D);
//循环左移动
void lMove(int *C, int *D, int moveBit);
//子密钥生成
void setIkey(int *keyBit, int iKey[16][48]);
//轮函数F
void lunF(int *R, int *iKey);
//字符转位
void charToBit(char *input , int *output, int length);
//位转字符
void bitToChar(int *input, char *output, int length);
//des解密函数
void deDes(char *mingWen,char *ciphertext, char *keyBit);



//ip置换根据table确定
void doIp(int *array, int length, int *table){
    int temp[64] = {0};
    bitCopy(array, temp, 64);
    for(int i = 0; i < length; ++i){
        array[i] = temp[table[i] - 1];
    }
}

//整个程序的异或运算执行函数
void doXor(int *output, int *input, int length){

    for(int i=0; i48,方便后面与子密钥异或
void doE(int *R, int *eTemp, int length)
{
    for(int i = 0; i < length; ++i){
        eTemp[i] = R[E_Table[i] - 1];
    }
}

//S盒压缩 48——>32
void doS(int *R, int *eTemp)
{
    int i, x, y;
	//注意指针的移动步数
    for(i = 0; i < 8; ++i, eTemp += 6, R += 4){
        x = eTemp[0]*2 + eTemp[5];
        y = eTemp[1]*8 + eTemp[2]*4 + eTemp[3]*2 + eTemp[4];
   //    printf("%d %dn", x, y);
        char T = (char)S_Box[i][x][y];
        charToBit(&T, R, 4);
    }

}
//简单的P盒置换
void doP(int *array)
{
    int temp[32] = {0};
    bitCopy(array, temp, 32);
     for(int i = 0; i < 32; ++i){
        array[i] = temp[P_Table[i] - 1];
    }
}
//密钥的pc_1表置换,剔除奇偶校验位
void doPc_1(int *keyBit, int *output){
    for(int i = 0; i < 56; ++i){
        output[i] = keyBit[PC1_Table[i] - 1];
    }
}

//合并c,d两部分进行pc_2的置换 56——>48
void doPc_2(int *iKey, int *C, int *D){
    int temp[56]={0};
    bitCopy(C, temp, 28);
    bitCopy(D, temp+28, 28);
    for(int i=0; i<48; ++i){
        iKey[i] = temp[PC2_Table[i]-1];
    }
}

//密钥循环左移
void lMove(int *C, int *D, int moveBit){
    int temp[28] = {0};

    bitCopy(C, temp, 28);
    bitCopy(temp+moveBit, C, 28-moveBit);
    bitCopy(temp, C+28-moveBit, moveBit);


    bitCopy(D, temp, 28);
    bitCopy(temp+moveBit, D, 28-moveBit);
    bitCopy(temp, D+28-moveBit, moveBit);

}

//生成子密钥
void setIkey(int *keyBit, int iKey[16][48])
{
    int temp[56]={0};
    int C[28];
    int D[28];
    doPc_1(keyBit, temp);//先做pc1剔除校验位,在拆成两组
    bitCopy(temp, C, 28);
    bitCopy(temp+28, D, 28);
    for(int i=0; i<16; ++i){
        lMove(C, D, LOOP_Table[i]);
        doPc_2(iKey[i], C, D);
    }
}

void lunF(int *R, int *iKey)
{

    int eTemp[48]={0};
	//E盒扩展
    doE(R, eTemp, 48);
	//和密钥异或
    doXor(eTemp, iKey, 48);
    //S盒压缩
    doS(R, eTemp);
    //P盒压缩
    doP(R);

}


//字符转换为位方便加密
void charToBit(char *input , int *output, int length)
{
    int i=0;
    for(i=0;i < length;i++)
    {
         output[i]=(input[i/8]>>(i%8))&1;
    }

}
//位转字符,复原
void bitToChar(int *input, char *output, int length)
{
     int i;
     for(i=0;i<(length/8);i++)
     {
      output[i]=0;
     }
     for(i=0;i=0;i--)
     {
        bitCopy(L, temp, 32);
        lunF(L, iKey[i]);
        doXor(R, L, 32);
        bitCopy(R, L, 32);
        bitCopy(temp, R, 32);

     }

    doIp(cBit, 64, IPR_Table);

     printf("n");
     bitToChar(cBit, mingWen, 64);

}

void bitToHex(char *output, int *input, int length)
{
  int i;

  for(i=0;i9)
       {
            output[i]=output[i]%16+'7';
       }
       else
            output[i]=output[i]%16+'0';
  }

}

void hexToBit(int *output, char *input,int length)
{
  int i;
  for(i=0;i>(i%4))&0x01;
       }
       else
       {
            output[i]=((input[i/4]-'7')>>(i%4))&0x01;
       }
  }
}


int main(){

    int mingBit[64] = {0};
    char ciphertext[16];
    int keyBit[64] = {0};
    char mingWen[8]="lkw23333";
    char key[8]="ssssssss";
    char deKey[8];


    printf("明文为:n");
    for(int i = 0; i < 8; ++i)
    {
        printf("%c", mingWen[i]);
    }
    printf("n");

    charToBit(mingWen, mingBit, 64);
    charToBit(key, keyBit, 64);
    doDes(mingBit, ciphertext, keyBit);

    printf("加密后:n");
    for(int i = 0; i < 16; ++i)
    {
        printf("%c", ciphertext[i]);
    }
    printf("n");
    printf("请输入密钥解密:");
    gets(deKey);

    charToBit(deKey, keyBit, 64);
    deDes(mingWen, ciphertext, keyBit);
    printf("明文为:n");
    for(int i = 0; i < 8; ++i)
    {
        printf("%c", mingWen[i]);
    }
    printf("n");
    return 0;
}

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/384469.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号