2012-02-07 47 views
2

我目前正试图对DES的加密方案进行实施,但是我很早就遇到了问题。这是我第一次在程序中执行按位操作,而且我也不熟悉C语言。我应用排列及其反转,结果与输入不一样。DES - 位的排列和反转

我想要做的是对64位块应用初始置换和反置换。我有我想在数组输入中加密的64位数据块。根据置换表IP,我将第一个字节的第一位置于置换中的第58位。位2被发送到位50,依此类推。排列后,结果被分成两半,两侧交换。这将使它能够使用相同的算法,但IPinverse表。

include <stdio.h> 
include <stdlib.h> 

static unsigned char Positions[8] = {1,2,4,8,16,32,64,128}; 

int main() 
{ 
    unsigned char input[8] = {'a','b','c','d','e','f','g','h'}; 
    unsigned char permutation[8]; 
    unsigned char inverse[8]; 
    int i; 
    for (i = 0; i < 8; i++) { 
     permutation[i] = 0; 
     inverse[i] = 0; 
    } 

    int IP[8][8] ={{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}}; 

    int IPinverse[8][8] ={{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}}; 

    printf("\n Before: \n"); 
    for (i = 0; i < 8; i++) { 
     printf(" %c", input[i]); 
    } 

    // Initial permutation 
    int bit, newpos; 
    unsigned char desiredbit; 
    for (bit = 0; bit < 64; bit++) { 
     // Get the location for where the bit will be sent and translate it to array index 
     newpos = ((int)IP[bit/8][bit%8])-1; 
     // examine the bit we're currently considering 
     desiredbit = input[bit/8] & Positions[bit%8]; 
     // if equal to zero that means no change necessary 
     if (desiredbit != 0) { 
       // else it was a 1 and we need to set the appropriate bit to 1 
       desiredbit = Positions[newpos%8]; 
       permutation[newpos/8] = desiredbit^permutation[newpos/8]; 
     } 
    } 

    printf("\n Permutation: \n"); 
    for (i = 0; i < 8; i++) { 
     printf(" %c", permutation[i]); 
    } 

    // Perform swap 
    unsigned char tempcopy[4] = {0,0,0,0}; 
    int j; 
    for (j = 0; j < 4; j++) { 
     tempcopy[j] = permutation[j+4]; 
    } 
    for (j = 0; j < 4; j++) { 
     permutation[j+4] = permutation[j]; 
     permutation[j] = tempcopy[j]; 
    } 

    // Reverse Permutation, remember to swap left side with right 
    for (bit = 0; bit < 64; bit++) { 
     newpos = ((int)IPinverse[bit/8][bit%8])-1; 
     desiredbit = permutation[bit/8] & Positions[bit%8]; 
     if (desiredbit != 0) { 
       desiredbit = Positions[newpos%8]; 
       inverse[newpos/8] = desiredbit^inverse[newpos/8]; 
     } 
    } 

printf("\n Reverse Permutation: \n"); 
    for (i = 0; i < 8; i++) { 
     printf(" %c", inverse[i]); 
    } 

    return 0; 

}

+0

它做的对吗?它从哪里开始失败? – KevinDTimm 2012-02-07 19:00:28

回答

1
  1. 你排列包含1索引64,但在使用它们的方式,他们应该是0到63
  2. 什么是用于交换?如果你排列,交换,然后排列,你不会到达同一个地方。
  3. 您需要验证置换和反转确实是相反的。我肯定不会去检查所有数字并进行验证。
+0

1.您可以看到所有索引都减1,从而将它们转换为0-63。 2.交换结果是错误。它应该用于最后的置换,当16轮加密已经应用于初始置换时。删除交换解决了问题。 3.表格是正确的。它们是DES加密中使用的表格的精确副本。 [链接] http://en.wikipedia.org/wiki/DES_supplementary_material#Final_permutation_.28IP-1.29 – Steinin 2012-02-07 19:14:48

+0

1中3结束了足够好。 – ugoren 2012-02-07 19:29:40