Java 中的 Mutliround Feistel 网络

Mutliround Feistel network in Java

对于一些学生的东西,我需要在 Java 中实现一个 Feistel 网络。

我从 3 轮手动开始,如下所示:

    // round 1
    int[] left1 = right;
    int[] right1 = new int[right.length];

    for(int i = 0; i < right.length; i++){
        right1[i] = left[i] ^ (right[i] ^ keys[0]);
    }

    // round 2
    int[] left2 = right1;
    int[] right2 = new int[right.length];

    for(int i = 0; i < right.length; i++){
        right2[i] = left1[i] ^ (right1[i] ^ keys[1]);
    }

    // round 3
    int[] left3 = right2;
    int[] right3 = new int[right.length];

    for(int i = 0; i < right.length; i++){
        right3[i] = left2[i] ^ ( right2[i] ^ keys[2]);
    }

如果我想进行 10 轮,我需要将这些东西复制 10 次并调整变量,有没有更好的方法来做到这一点?也许为时已晚,但我想不出解决办法...

您可以简单地向前和向后交换:

//initialization
int[] left = {};//setup left
int[] right = {};//setup right
//keys
int[] keys = {};//setup keys

for(int r = 0; r < 10; r++) {//the number of rounds
    for(int i = 0; i < right.length; i++){
        right[i] = left[i] ^ (right[i] ^ keys[r]);
    }

    //swap lists to do the next round
    int[] temp = left;
    left = right;
    right = temp;
}
//remark: the result (right) will be stored in left
//use left as resulting right

每一轮之后,您通过在参考级别左右交换(并使用 temp)来临时存储参考:

int[] temp = left;
left = right;
right = temp;

请注意,您不会复制 此处的值,您只是交换引用,因此这是在常数时间内完成的。如果您想要 encrypt/decrypt 长消息并且不想浪费时间再次复制,这会很有用。

那么发生的事情是,您最初有三个列表 L、R 和 K

现在在第一轮中,您只需按元素修改提升列表,如代码中所示:

for(int i = 0; i < right.length; i++){
    right[i] = left[i] ^ (right[i] ^ keys[r]);
}

重要的是你不写keys[i],而是使用keys[r](索引是当前回合):这意味着你至少有10个键来做当然是算术。

请注意,您可以覆盖 right[i],因为您以后不会重复使用该值。因此,您可以进行内联修改。

修改后,交换缓冲区。您需要考虑的唯一方面是在最后一轮,在执行操作后,缓冲区也将被交换。因此最后的 leftright 也将被交换。您可以 (1) 在 for 循环之后进行额外的交换;或 (2) 考虑交换并假装 leftright,反之亦然;或 (3) 使用 if 子句来防止最后一次交换。

使用二维数组

int rounds = 10 // number of rounds
int leftArray = new int[rounds][right.length];
int rightArray = new int[rounds][right.length];

然后:

  • leftArray[0][0] 等同于 left1[0];
  • leftArray[0][1] 等同于 left1[1];
  • rightArray[0][0] 等同于 right1[0];
  • rightArray[2][2] 等同于 right3[2];
  • ...

然后使用嵌套循环迭代你需要做的事情

for(int i=0; i<rouds; i++){
  //set your variables
  for(int j=0; j<right.length; j++){
  //do computation here
  }
}