IDEA加密算法,本人新手,最好能有详细说明。
本人想开发一个BS客户端加密,服务器端解密的登录系统。
客户端准备使用JS编写加密算法,服务器端准备用C#编写服务器端解密算法。
现征求:
JavaScript的IDEA客户端加密算法和C#的服务器端解密算法!若谁有现成的登录系统,可以发到我邮箱,分不够,可以另开新帖!
本人想开发一个BS客户端加密,服务器端解密的登录系统。
客户端准备使用JS编写加密算法,服务器端准备用C#编写服务器端解密算法。
现征求:
JavaScript的IDEA客户端加密算法和C#的服务器端解密算法!若谁有现成的登录系统,可以发到我邮箱,分不够,可以另开新帖!
Windows, Messages, SysUtils, Classes,Dialogs;
function BinToHex(strBin:string):string;
function HexToTen(strHex:string):int64;
function LeftMove(S:string;P:integer):String;
function ModAdd(intAdd1,intAdd2:int64):int64;
function ModMul(intMul1,intMul2:int64;intFlag:integer):int64;
function ModXor(intXor1,intXor2:int64):int64;
procedure CreatePassword(strPassword:string;VAR arrPassword:array of int64;VAR arrOpenPassword:array of int64); //产生加密子密钥函数
procedure GetOpenPassword(intSource:int64;VAR intResult:int64;Flag:integer); //求取解密子密钥函数
procedure CreateKeyTable(); //产生加、解密子密钥之间的对应关系表
procedure Riddle(arrPassword:array of int64;arrRiddleKey:array of int64;VAR arrOpenPassword:array of int64);StdCall;export; //IDEA数据解密函数
procedure CreateOpenPassword(VAR arrOpenPassKey:array of int64); //产生解密子密钥函数
procedure CreateKey(VAR arrKey:array of int64;VAR arrOpenKey:array of int64;VAR strOutKey:string);StdCall;export; //产生加密密钥函数
implementationConst strNum:array[1..16] of string[4]=('0000','0001','0010','0011','0100','0101','0110','0111','1000','1001','1010','1011','1100','1101','1110','1111');
Const chrHex:array[1..16] of char=('0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F');
var
g_arr_Ten_Password:array[1..52] of int64;
g_arr_Flag:array[1..52] of integer;
g_arr_Table:array[1..52] of integer;
...{--------------------------------------------------------------------}procedure CreateKey(VAR arrKey:array of int64;VAR arrOpenKey:array of int64;VAR strOutKey:string);StdCall;export;
var
intKey,intLoop1,intLoop2,intLoop3:integer;
hexKey,ch,strTemp:string;
strKey:string[128];
begin
strKey:='';
Randomize;
for intLoop1:=1 to 8 do
begin
intKey:=Random(65536);
hexKey:=IntToHex(intKey,4);
strTemp:='';
for intLoop2:=1 to 4 do
begin
ch:=Copy(hexKey,intLoop2,1);
for intLoop3:=1 to 16 do
begin
if ch = chrHex[intLoop3] then
begin
ch:= strNum[intLoop3];
break;
end;
end;
strTemp:=strTemp+ch;
end;
strKey:=strKey+strTemp;
end;
strOutKey:=strKey;
CreatePassword(strKey,arrKey,arrOpenKey); //调用产生加密子密钥过程
end;
...{--------------------------------------------------------------------}function BinToHex(strBin:string):string;
var
intLoop1,intLoop2:integer;
strTemp,strResult:string;
begin
intLoop1:=1;
strResult:='';
if Length(strBin) <> 16 then ShowMessage('二进制数据长度有错!');
while (intLoop1<=16) do
begin
strTemp:=Copy(strBin,intLoop1,4);
for intLoop2:=1 to 16 do
if strTemp=strNum[intLoop2] then
begin
strTemp:=chrHex[intLoop2];
break;
end;
strResult:=strResult+strTemp;
intLoop1:=intLoop1 + 4;
end;
BinToHex:=strResult;
end;
...{--------------------------------------------------------------------}function HexToTen(strHex:string):int64; //十六进制转十进制
var
intLoop1,intLoop2,intTemp:integer;
intResult:int64;
strTemp:string;
begin
intResult:=0;
intTemp:=0;
if Length(strHex) <> 4 then ShowMessage('十六进制数据长度有错!');
for intLoop1:=1 to 4 do
begin
Case intLoop1 of
1:intTemp:=4096;
2:intTemp:=256;
3:intTemp:=16;
4:intTemp:=1
end;
strTemp:=Copy(strHex,intLoop1,1);
for intLoop2:=1 to 16 do
if UpperCase(strTemp) = chrHex[intLoop2] then
begin
intResult:=intResult+(Int64(intLoop2) - 1)*Int64(intTemp);
break;
end;
end;
HexToTen:=intResult;
end;
...{--------------------------------------------------------------------}function LeftMove(S:string;P:integer):String;
var
int_Len,i:integer;
str_Result,str_Num:string;
begin
int_Len:=length(s);
str_Num:=S;
str_Result:='';
if int_Len <= P then
str_Result :=S
else
begin
for i:=P+1 to int_Len do
str_Result:=str_Result+copy(str_Num,i,1);
str_Result:=str_Result+copy(str_Num,1,p);
end;
LeftMove:=Trim(str_Result);
end;
...{--------------------------------------------------------------------}function ModAdd(intAdd1,intAdd2:int64):int64;
begin
ModAdd:=(intAdd1 + intAdd2) mod 65536; //模65536求和
end;function ModMul(intMul1,intMul2:int64;intFlag:integer):int64;
var intTemp:int64;
begin
intTemp:=(intMul1 * intMul2) mod 65537;
if intFlag = 0 then
begin
if intMul1 = 0 then intTemp:=65537 - intMul2;
if intMul2 = 0 then intTemp:=65537 - intMul1;
if intTemp = 65536 then intTemp:=0;
if intTemp = 65537 then intTemp:=1;
end
else
begin
if intMul1 = 0 then intTemp:=65537 - intMul2;
if intMul2 = 0 then intTemp:=65537 - intMul1;
if intTemp = 0 then intTemp:=65536;
if intTemp = 65537 then intTemp:=1;
if intTemp = 65536 then intTemp:=0;
end;
ModMul:=intTemp;
end;function ModXor(intXor1,intXor2:int64):int64;
begin
ModXor:= intXor1 xor intXor2;
end;
...{--------------------------------------------------------------------}procedure CreatePassword(strPassword:string;VAR arrPassword:array of int64;VAR arrOpenPassword:array of int64);
var
strKey:string;
strTemp:array[1..52] of string[4];
intStart,intCount:integer;
begin
strKey:=strPassword; //
intCount:=1;
intStart:=1;
...{--------------------产生52个16bit的加密子密钥部分-------------------}
while (intCount<=52) do
begin
strTemp[intCount]:=BinToHex(Copy(strKey,intStart,16));
intStart:=intStart+16;
intCount:=intCount+1;
if ((intCount mod 8) = 1) then
begin
strKey:=LeftMove(strKey,25);
intStart:=1;
end;
end;
intCount:=1;
while (intCount<=52) do
begin
arrPassword[intCount-1]:=HexToTen(strTemp[intCount]);
g_arr_Ten_Password[intCount]:=arrPassword[intCount-1];
intCount:=intCount+1;
end;
CreateOpenPassword(arrOpenPassword);
...{--------------------产生52个16bit的加密子密钥部分-------------------}
end;
...{--------------------------------------------------------------------}procedure GetOpenPassword(intSource:int64;VAR intResult:int64;Flag:integer);
var
int_Source,int_Result,int_Mod_Value:int64;
int_Loop:integer;
begin
int_Source:=intSource;
...{--------------------求取每个加密子密钥相应的解密子密钥部分-------------------}
Case Flag of
0: intResult:=int_Source;
1: intResult:=65536-int_Source;
2:
begin
if int_Source=0 then
intResult:=int_Source
else
for int_Loop:=1 to 65536 do
begin
int_Result:=Int64(int_Loop)*65537+1;
int_Mod_Value:=int_Result mod int_Source;
if int_Mod_Value = 0 then
begin
int_Result:=int_Result div int_Source;
intResult:=int_Result;
break;
end;
end;
end;
end;
...{--------------------求取每个加密子密钥相应的解密子密钥部分-------------------}
end;
...{--------------------------------------------------------------------}
var
int_Count_CreatePassword,int_Count_OpenPassword,int_ExChange:integer;
begin
...{----------------求取在产生解密子密钥时所用的参数标志对应表部分-------------}
for int_Count_CreatePassword:=52 downto 1 do
Case int_Count_CreatePassword mod 6 of
0,5:begin g_arr_Flag[int_Count_CreatePassword]:=0; end;
2,3:begin g_arr_Flag[int_Count_CreatePassword]:=1; end;
1,4:begin g_arr_Flag[int_Count_CreatePassword]:=2; end;
end;
...{----------------求取在产生解密子密钥时所用的参数标志对应表部分-------------}...{----------------求取每个加密子密钥与相应解密子密钥间的对应关系映射表部分-------------}
int_Count_CreatePassword:=52;
int_Count_OpenPassword:=1;
while (int_Count_CreatePassword>=1) do
begin
Case int_Count_CreatePassword mod 6 of
1,2,3,4:
begin
g_arr_Table[int_Count_OpenPassword]:=int_Count_CreatePassword-3;
g_arr_Table[int_Count_OpenPassword+1]:=int_Count_CreatePassword-1;
g_arr_Table[int_Count_OpenPassword+2]:=int_Count_CreatePassword-2;
g_arr_Table[int_Count_OpenPassword+3]:=int_Count_CreatePassword;
if (int_Count_CreatePassword >=48) or (int_Count_CreatePassword <=4 ) then //首轮和末轮处理不需交换,故要再换回来
begin
int_ExChange:=g_arr_Table[int_Count_OpenPassword+1];
g_arr_Table[int_Count_OpenPassword+1]:=g_arr_Table[int_Count_OpenPassword+2];
g_arr_Table[int_Count_OpenPassword+2]:=int_ExChange;
end;
int_Count_CreatePassword:=int_Count_CreatePassword-4;
int_Count_OpenPassword:=int_Count_OpenPassword+4;
end;
0,5:
begin
g_arr_Table[int_Count_OpenPassword]:=int_Count_CreatePassword-1;
g_arr_Table[int_Count_OpenPassword+1]:=int_Count_CreatePassword;
int_Count_CreatePassword:=int_Count_CreatePassword-2;
int_Count_OpenPassword:=int_Count_OpenPassword+2;
end;
end;
end;
...{----------------求取每个加密子密钥与相应解密子密钥间的对应关系映射表部分-------------}
end;
...{--------------------------------------------------------------------}
procedure CreateOpenPassword(VAR arrOpenPassKey:array of int64);
var
int_Loop:integer;
arrTemp:array[1..52] of int64;
begin
...{-------------通过调用产生加、解密子密钥对应关系函数产生对应关系表部分------------------}
CreateKeyTable;
...{-------------通过调用求解解密子密钥函数产生解密子密钥部分------------------}
for int_Loop:=1 to 52 do
begin
GetOpenPassword(g_arr_Ten_Password[int_Loop],arrTemp[g_arr_Table[int_Loop]],g_arr_Flag[int_Loop]);
end;
for int_Loop:=1 to 52 do
arrOpenPassKey[int_Loop-1]:=arrTemp[int_Loop];
...{-------------通过调用求解解密子密钥函数产生解密子密钥部分------------------}
end;
...{--------------------------------------------------------------------}procedure Riddle(arrPassword:array of int64;arrRiddleKey:array of int64;VAR arrOpenPassword:array of int64);
var
Count,i:integer;
V1,V2,V3,V4,V5,V6,V7,V8,V9,V10,V11,V12,V13,V14,C1,C2,C3,C4,ExChange:int64;
P:array[1..4] of int64;
begin
...{------------------------数据 "解密" 算法实现部分------------------}
for i:=Low(arrPassword) to High(arrPassword) do
P[i+1]:=arrPassword[i];
Count:=0;
while (Count<48) do
begin
V1:= ModMul(P[1],arrRiddleKey[Count],1); //相乘 1
Inc(Count);
V2:= ModAdd(P[2],arrRiddleKey[Count]); //相加 2
Inc(Count);
V3:= ModAdd(P[3],arrRiddleKey[Count]); //相加 3
Inc(Count);
V4:= ModMul(P[4],arrRiddleKey[Count],1); //相乘 4
Inc(Count);
V5:= ModXor(V1,V3); //异或 5
V6:= ModXor(V2,V4); //异或 6
V7:= ModMul(V5,arrRiddleKey[Count],1); //相乘 7
Inc(Count);
V8:= ModAdd(V6,V7); //相加 8
V9:= ModMul(V8,arrRiddleKey[Count],1); //相乘 9
Inc(Count);
V10:=ModAdd(V7,V9); //相加 10
V11:=ModXor(V1,V9); //异或 11
V12:=ModXor(V2,V10); //异或 12
V13:=ModXor(V3,V9); //异或 13
V14:=ModXor(V4,V10); //异或 14
P[1]:=V11;
P[2]:=V13; //注意:交换中间两个输出结果
P[3]:=V12; //注意:交换中间两个输出结果
P[4]:=V14;
end; //结束8轮计算
ExChange:=P[2];
P[2]:=P[3];
P[3]:=ExChange; //因为最后一轮无需转换,所以必须把P[2],P[3]再次转换回来
C1:= ModMul(P[1],arrRiddleKey[48],1); //相乘 1
C2:= ModAdd(P[2],arrRiddleKey[49]); //相加 2
C3:= ModAdd(P[3],arrRiddleKey[50]); //相加 3
C4:= ModMul(P[4],arrRiddleKey[51],1); //相乘 4
...{------------------------数据 "解密" 算法实现部分------------------}
arrOpenPassword[Low(arrOpenPassword)]:=C1;
arrOpenPassword[Low(arrOpenPassword)+1]:=C2;
arrOpenPassword[Low(arrOpenPassword)+2]:=C3;
arrOpenPassword[Low(arrOpenPassword)+3]:=C4;
//数据解密成功!
end;
...{--------------------------------------------------------------------}end.
/获得被加密文件名
string MyInFileName=this.textBox1.Text;
//获得加密输出文件名
string MyOutFileName=this.textBox2.Text;
//设定初始向量
byte[] MyDESIV={0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08};
byte[] MyDESKey={};
//根据密码设置密钥大小
string MyKeyString=this.textBox3.Text;
if (MyKeyString.Length==6)
{
MyDESKey=new byte[]{(byte)MyKeyString[0],(byte)MyKeyString[1],(byte)MyKeyString[2],
(byte)MyKeyString[3],(byte)MyKeyString[4],(byte)MyKeyString[5],
0x07,0x08};
}
if (MyKeyString.Length==7)
{
MyDESKey=new byte[]{(byte)MyKeyString[0],(byte)MyKeyString[1],(byte)MyKeyString[2],
(byte)MyKeyString[3],(byte)MyKeyString[4],(byte)MyKeyString[5],
(byte)MyKeyString[6],0x07};
}
if (MyKeyString.Length>=8)
{
MyDESKey=new byte[]{(byte)MyKeyString[0],(byte)MyKeyString[1],(byte)MyKeyString[2],
(byte)MyKeyString[3],(byte)MyKeyString[4],(byte)MyKeyString[5],
(byte)MyKeyString[6],(byte)MyKeyString[7]};
}
//创建输入和输出文件流
FileStream MyInFileStream = new FileStream(MyInFileName, FileMode.Open, FileAccess.Read);
FileStream MyOutFileStream = new FileStream(MyOutFileName, FileMode.OpenOrCreate, FileAccess.Write);
MyOutFileStream.SetLength(0);
//每次的中间流.
byte[] InsertData = new byte[100];
//代表已经加密流的大小
int CompletedLength=0;
//代表要加密文件总的大小
long InFileSize = MyInFileStream.Length;
//创建DES对象
DES MyDES = new DESCryptoServiceProvider();
//创建加密流
CryptoStream EncryptStream = new CryptoStream(MyOutFileStream, MyDES.CreateEncryptor(MyDESKey, MyDESIV), CryptoStreamMode.Write);
//从输入文件中读取流,然后加密到输出文件中
while(CompletedLength < InFileSize)
{ //每次写入加密文件的数据大小
int Length= MyInFileStream.Read(InsertData, 0, 100);
EncryptStream.Write(InsertData, 0, Length);
CompletedLength = CompletedLength + Length;
}
//关闭流
EncryptStream.Close();
MyOutFileStream.Close();
MyInFileStream.Close();
MessageBox.Show("文件加密已经操作成功!","信息提示",MessageBoxButtons.OK,MessageBoxIcon.Information); ///////////////////////////////////////解密文件//////////////////////////////////////////////////////////////////////////////
//获得要解密的文件名
string MyInFileName=this.textBox8.Text;
//获得要保存的文件名
string MyOutFileName=this.textBox7.Text;
//设定初始向量
byte[] MyDESIV={0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08};
byte[] MyDESKey={};
//根据密码算出密钥
string MyKeyString=this.textBox6.Text;
if (MyKeyString.Length==6)
{
MyDESKey=new byte[]{(byte)MyKeyString[0],(byte)MyKeyString[1],(byte)MyKeyString[2],
(byte)MyKeyString[3],(byte)MyKeyString[4],(byte)MyKeyString[5],
0x07,0x08};
}
if (MyKeyString.Length==7)
{
MyDESKey=new byte[]{(byte)MyKeyString[0],(byte)MyKeyString[1],(byte)MyKeyString[2],
(byte)MyKeyString[3],(byte)MyKeyString[4],(byte)MyKeyString[5],
(byte)MyKeyString[6],0x07};
}
if (MyKeyString.Length>=8)
{
MyDESKey=new byte[]{(byte)MyKeyString[0],(byte)MyKeyString[1],(byte)MyKeyString[2],
(byte)MyKeyString[3],(byte)MyKeyString[4],(byte)MyKeyString[5],
(byte)MyKeyString[6],(byte)MyKeyString[7]};
}
//创建输入和输出文件流
FileStream MyInFileStream = new FileStream(MyInFileName, FileMode.Open, FileAccess.Read);
FileStream MyOutFileStream = new FileStream(MyOutFileName, FileMode.OpenOrCreate, FileAccess.Write);
MyOutFileStream.SetLength(0);
//每次的中间流.
byte[] InsertData = new byte[100];
//代表已经解密的流的大小
int MyCompletedSize=0;
//代表要解密文件总的大小
long MyFileSize = MyInFileStream.Length;
//创建DES对象
DES MyDES= new DESCryptoServiceProvider();
//创建解密流
CryptoStream DecryptStream = new CryptoStream(MyOutFileStream, MyDES.CreateDecryptor(MyDESKey,MyDESIV), CryptoStreamMode.Write);
//从输入文件中读取流,然后解密到输出文件中
while(MyCompletedSize < MyFileSize)
{ //每次写入解密流的大小
int length = MyInFileStream.Read(InsertData, 0, 100);
DecryptStream.Write(InsertData, 0, length);
MyCompletedSize=MyCompletedSize+length;
}
//关闭流
DecryptStream.Close();
MyOutFileStream.Close();
MyInFileStream.Close();
MessageBox.Show("文件解密操作成功!","信息提示",MessageBoxButtons.OK,MessageBoxIcon.Information);