package util;
import converter.MyConverter;
public class Converter {
/**
* 解密进行密钥的每一次置换
* @param data 一组密文
* @param count 轮数
* @param everyKey 子密钥与加密相反
*/
public static String DecryptEveryChange(int[] data,int count,int[][] everyKey)
{
int[][] keys=new int[16][48];
//逆置密钥
for (int i = 0; i < 16; i++) {
for (int j = 0; j < 48; j++) {
keys[i][j]=everyKey[15-i][j];
}
}
int[] left=new int[32];
int[] right=new int[32];
int[] left1=new int[32];
int[] right1=new int[32];
int[] result=new int[64];
for (int i = 0; i < right1.length; i++) {
right[i]=data[i];
left[i]=data[i+32];
}
int[] temp=SBoxAndP(EAndXOR(left, count, keys));
left1=XOR(temp,right);
for(int i=0;i<32;i++)
{
right1[i]=left[i];
}
if(count==15)
{
for(int j=0;j<32;j++)
{
data[j]=left1[j];
data[j+32]=right1[j];
}
}
else
{
for(int j=0;j<32;j++)
{
data[j]=right1[j];
data[j+32]=left1[j];
}
}
for (int i = 0; i < data.length; i++) {
result[i]=data[MyConverter.IP_1[i]-1];
}
return Transform._2TransfromString(result);
}
/**
* 加密进行密钥的每一次置换
* @param data 一组明文
* @param count 轮数
* @param everyKey 子密钥
*/
public static String EncryptEveryChange(int[] data,int count,int[][] everyKey)
{
int[] left=new int[32];
int[] right=new int[32];
int[] left1=new int[32];
int[] right1=new int[32];
int[] result=new int[64];
for (int i = 0; i < right1.length; i++) {
left[i]=data[i];
right[i]=data[i+32];
}
int[] temp=SBoxAndP(EAndXOR(right, count, everyKey));
right1=XOR(temp,left);
for(int i=0;i<32;i++)
{
left1[i]=right[i];
}
if(count==15)
{
for(int j=0;j<32;j++)
{
data[j]=right1[j];
data[j+32]=left1[j];
}
}
else
{
for(int j=0;j<32;j++)
{
data[j]=left1[j];
data[j+32]=right1[j];
}
}
for (int i = 0; i < data.length; i++) {
result[i]=data[MyConverter.IP_1[i]-1];
}
return Transform._2TransfromString(result);
}
/**
* s盒代替48->32 p盒置换
* @param data
* @return
*/
public static int[] SBoxAndP(int[] data)
{
int[][] s=new int[8][6];
int[]s_after=new int[32];
int[] result=new int[32];
for(int i=0;i<8;i++){
System.arraycopy(data,i*6,s[i],0,6);
int r=(s[i][0]<<1)+ s[i][5];//横坐标
int c=(s[i][1]<<3)+(s[i][2]<<2)+(s[i][3]<<1)+s[i][4];//纵坐标
String str=Integer.toBinaryString(MyConverter.S_Box[i][r][c]);
while (str.length()<4){
str="0"+str;
}
for(int j=0;j<4;j++){
int p=Integer.valueOf(str.charAt(j));
if(p==48){
p=0;
}else if(p==49){
p=1;
}else{
System.out.println("To bit error!");
}
s_after[4*i+j]=p;
}
}
/******S盒替换结束*******/
/****P盒替代****/
for(int i=0;i<32;i++){
result[i]=s_after[MyConverter.P[i]-1];
}
return result;
}
/**
* 对右半部分进行扩展32-》48同时进行与密钥异或
* @param right
* @param count
* @param everyKey
* @return
*/
public static int[] EAndXOR(int[] right,int count,int[][] everyKey)
{
int[] resultSet=new int[48];
for(int i=0;i<48;i++)
{
resultSet[i]=right[MyConverter.E[i]-1];
}
int[] result=XOR(resultSet, everyKey[count]);
return result;
}
/**
* 异或
* @param a
* @param b
* @return
*/
public static int[] XOR(int[] a,int[] b)
{
int[] result=new int[b.length];
for (int i = 0; i < b.length; i++) {
result[i]=a[i]+b[i];
if(a[i]+b[i]==2)
{
result[i]=0;
}
}
return result;
}
/**
* 密钥置换之后移位,分左右两个部分,分别进行移位
* @param key 置换后的密钥
* @param count 第count轮运算
*/
public static void LeftMove(int[] key,int count)
{
int[] left=new int[28];
int[] right=new int[28];
int[] left1=new int[28];
int[] right1=new int[28];
for(int i=0;i<left.length;i++)
{
left[i]=key[i];
right[i]=key[i+28];
}
if(MyConverter.LFT[count]==1)
{
for(int i=0;i<left.length-1;i++)
{
left1[i]=left[i+1];
right1[i]=right[i+1];
}
left1[27]=left[0];
right1[27]=right[0];
}
if(MyConverter.LFT[count]==2)
{
for(int i=0;i<left.length-2;i++)
{
left1[i]=left[i+2];
right1[i]=right[i+2];
}
left1[27]=left[1];
right1[27]=right[1];
left1[26]=left[0];
right1[26]=right[0];
}
for(int i=0;i<left.length;i++)
{
key[i]=left1[i];
key[i+28]=right1[i];
}
}
/**
*
* @param key 原始密钥
* @return
*/
public static int[] PC(int[] key)
{
int[] result=new int[56];
for (int i = 0; i < result.length; i++) {
result[i]=key[MyConverter.PC1[i]-1];
}
return result;
}
}