?? form1.cs
字號:
this.label8.Size = new System.Drawing.Size(296, 32);
this.label8.TabIndex = 3;
this.label8.Text = "DES分組解密=》帶有時間戳明文=》MD5摘要生成";
//
// label7
//
this.label7.Location = new System.Drawing.Point(72, 128);
this.label7.Name = "label7";
this.label7.Size = new System.Drawing.Size(296, 24);
this.label7.TabIndex = 4;
this.label7.Text = "發送者公鑰得到明文摘要";
//
// label9
//
this.label9.Location = new System.Drawing.Point(344, 112);
this.label9.Name = "label9";
this.label9.Size = new System.Drawing.Size(256, 24);
this.label9.TabIndex = 5;
this.label9.Text = "摘要對比 =》提取驗證時間戳=》得到明文";
//
// Form1
//
this.AutoScaleBaseSize = new System.Drawing.Size(6, 14);
this.ClientSize = new System.Drawing.Size(640, 438);
this.Controls.Add(this.CreateXmlKeys);
this.Controls.Add(this.button2);
this.Controls.Add(this.button1);
this.Controls.Add(this.tabControl1);
this.Controls.Add(this.richbox);
this.Name = "Form1";
this.Text = "Form1";
this.groupBox1.ResumeLayout(false);
this.tabControl1.ResumeLayout(false);
this.tabPage1.ResumeLayout(false);
this.tabPage2.ResumeLayout(false);
this.groupBox4.ResumeLayout(false);
this.groupBox3.ResumeLayout(false);
this.groupBox2.ResumeLayout(false);
this.tabPage3.ResumeLayout(false);
this.groupBox5.ResumeLayout(false);
this.ResumeLayout(false);
}
#endregion
/// <summary>
/// 應用程序的主入口點。
/// </summary>
[STAThread]
static void Main()
{
Application.Run(new Form1());
}
byte [] fileContents;//=null;//儲存原始的明文數據
//打開文件
private void OpenFileBtn_Click(object sender, System.EventArgs e)
{
OpenFileDialog open = new OpenFileDialog();
open.Title = "請打開你要產生摘要的文件:";
open.Filter = "All File (*.*)|*.*";
if(open.ShowDialog()==DialogResult.OK)
{
FileName.Text = open.FileName ;
richbox.AppendText("\n你選擇了要進行散列的文件:" + FileName.Text);
}
else
{
return ;
}
}
private void SendFileToDTS_Click(object sender, System.EventArgs e)
{
try
{
//讀取文件內容到一數組里
FileStream fs = new FileStream(FileName.Text,FileMode.Open,FileAccess.Read);
byte [] ifileContent = new byte[(int)fs.Length];
fs.Read(ifileContent,0,(int)fs.Length);
fs.Close(); //讀取到數組中去
fileContents = ifileContent ;
}
catch
{
richbox.AppendText("\n讀取文件失敗,請仔細查找原因!");
}
byte [] HashValue = null;
try
{//產生文件散列
HashValue = ShareClass.HashFile(0,FileName.Text);
richbox.AppendText("\n已經產生了文件散列 :\n 散列長度:"+ HashValue.Length.ToString() +"\n散列:\n"+Convert.ToBase64String(HashValue,0,HashValue.Length)/* System.Text.Encoding.Default.GetString(HashValue)*/);
}
catch
{
richbox.AppendText("\n計算文件散列失敗!");
}
//DTS獲取收到文件時間
byte [] TimeNow = ShareClass.GetTimeNow();
richbox.AppendText("\n時間數組長度--TimeNow: "+ TimeNow.Length.ToString());
//把時間加進散列中
byte[]HashAndTime = ShareClass.CombinBytes(TimeNow,HashValue);
richbox.AppendText("\n接受到數據時間: " + System.Text.Encoding.Default.GetString(TimeNow) + " \n已經加進到文件摘要中!");
//簽名簽名數組
byte [] signHash = ShareClass.Sinature(ShareClass.OpenFile("DTSPrivateKey.txt"),HashAndTime );
richbox.AppendText("\n已經為文件簽名!\n簽名長度--signHash:" + signHash.Length.ToString());
//合并成DTS時間戳格式數組
byte [] combinData = ShareClass.CombinBytes(signHash,HashAndTime);
try
{
fileContents = ShareClass.CombinBytes(combinData,fileContents); //加進時間戳
richbox.AppendText("\n現已把時間戳添加到文件中去!");
}
catch
{richbox.AppendText("\n添加時間戳失敗!");}
}
//錯誤的原因:不正確的數組長度。
private void StartStepsBtn_Click(object sender, System.EventArgs e)
{
//產生隨機的密碼和向量
byte[]Key =ShareClass.RandomKey(0);
byte[]IV =ShareClass.RandomIV(0);
richbox.AppendText("\n產生了隨機密碼:KEY 和向量:IV!\nKey and IV Size: " + Key.Length.ToString() +" "+IV.Length.ToString());
//對隨機密碼和向量進行簽名和加密
byte [] KeyAndIV = ShareClass.CombinBytes(IV,Key);//這里把Key和IV合并一起
richbox.AppendText("\nKeyAdnIV Size : "+KeyAndIV.Length.ToString() );
//把整個密碼參數簽名
byte [] Signature = ShareClass.Sinature(ShareClass.OpenFile("A_PrivateKey.txt"),KeyAndIV);
richbox.AppendText("\n簽名整個密碼參數-KeyAndIV : Signature Size: "+ Signature.Length.ToString());
//合并密碼參數和簽名
byte [] KeyAndSignature = ShareClass.CombinBytes(Signature,KeyAndIV);
//使用B的公鑰加密密碼和密碼簽名數組
byte [] RsaEncryptData = ShareClass.RsaEncrypt(ShareClass.OpenFile("B_PublicKey.txt"),KeyAndSignature);//Signature); //對已經簽名的數據進行非對稱加密處理
richbox.AppendText("\n對已經簽名的密碼數據進行非對稱加密處理--信封處理 \n數字信封的長度: RsaEncryptData : " + RsaEncryptData.Length.ToString());
// ShareClass.WriteFile(FileName.Text+".enc",RsaEncryptData); //寫進文件:數字信封
//對稱加密已經加進時間戳的明文
// ShareClass.EncryptFile(0,FileName.Text,FileName.Text+".enc",Key,IV); //把對文件加密后的的數據寫進文件
//int choice,string filename,byte[]Key,byte[]IV
//對含時間戳的明文進行DES分組加密
byte [] EncryptionDate = ShareClass.EncryptFile(0,fileContents,Key,IV);//加密加時間戳的明文
richbox.AppendText("\n加密已經加進時間戳的明文,使用隨機產生的密碼和向量:KEY、IV ");
richbox.AppendText("密文長度:EncryptionDate: "+EncryptionDate.Length.ToString());
//對含時間戳的明文進行摘要
byte [] HashFile = ShareClass.HashData(0,fileContents);//HashFile(0,FileName.Text); //計算摘要 //////////////////////////////////////////////
richbox.AppendText("\n計算已經加進時間戳的明文摘要,摘要長度:HashFile :" + HashFile.Length.ToString());
//為摘要簽名
byte [] SignatureData = ShareClass.Sinature(ShareClass.OpenFile("A_PrivateKey.txt"),HashFile);
richbox.AppendText("\n對該摘要進行簽名,簽名長度:SignatureData:" +SignatureData.Length.ToString());
byte [] CombinData =ShareClass.CombinBytes(SignatureData,HashFile); //把摘要和簽名合并一起
richbox.AppendText("\n開始合并這三部分......\n長度:CombinData: "+ CombinData.Length.ToString());
//把加密結果寫進文件//要注意寫入的順序!
FileStream FS = new FileStream(FileName.Text+".enc",FileMode.Create,FileAccess.Write);
FS.Write( RsaEncryptData,0,RsaEncryptData.Length );
FS.Write( EncryptionDate,0,EncryptionDate.Length );//B_PrivateKey.txt
FS.Write( CombinData,0,CombinData.Length );
FS.Flush();
FS.Close();
string file = FileName.Text+".enc";
richbox.AppendText("\n合并結束!\n請查看合并結果文件:\n" +file + "\n三部分的長度分別為:\n" + "RsaEncryptData: " + RsaEncryptData.Length.ToString() +"\nEncryptionDate :" +EncryptionDate.Length.ToString() +"\nCombinData :" + CombinData.Length.ToString() );
int length = RsaEncryptData.Length+EncryptionDate.Length+CombinData.Length;//計算整個密文長度
richbox.AppendText("\n總的長度為: " + length.ToString());
}
private static bool state = true ;
private static RSACryptoServiceProvider icrypt ;//全局函數
private void button1_Click(object sender, System.EventArgs e)
{
if(state)
{
ShareClass.CreateXmlKey("PrivateKey.txt",icrypt.ToXmlString(true));
state = false ;
button1.Text = "產生公鑰";
}
else
{
ShareClass.CreateXmlKey("PublicKey.txt",icrypt.ToXmlString(false));
state = true ;
button1.Text = "產生私鑰";
button1.Enabled = false ;
}
}
private void button2_Click(object sender, System.EventArgs e)
{
icrypt = new RSACryptoServiceProvider();
button2.Enabled = false ;
}
//產生成對鑰匙
private static int i = 0 ;
private void CreateXmlKeys_Click(object sender, System.EventArgs e)
{
i ++ ;
icrypt = new RSACryptoServiceProvider();
ShareClass.CreateXmlKey("PublicKey" + i.ToString()+".txt",icrypt.ToXmlString(true));
ShareClass.CreateXmlKey( "PrivateKey"+ i.ToString()+".txt",icrypt.ToXmlString(false));
MessageBox.Show("產生第" + i.ToString() + "對私鑰和公鑰!" );
}
//把整個加密信息分解為三部分 //分別讀取到三不數組里面
private static byte [] Encrypt_One ,Encrypt_Two,Encrypt_Three ;
private void DepartBytes_Click(object sender, System.EventArgs e)
{
/* 這地方有兩種數據讀取方式:方式一,從文件中分離需要部分;方式二,把文件內容讀取到字節數組中,然后分離數組;我們使用方式一,個人認為提供效率!*/
//打開文件,直接從文件中讀取,出現錯誤啊
string fileName = OpenFile("請打開要解密的文件:");
//第一種讀取方式:直接從文件中讀取
FileStream fs = new FileStream(fileName,FileMode.Open,FileAccess.Read);
//第二種讀取方式:直接讀取到一個數組里面,然后對數組進行分解
// byte []fileContent = new byte[fs.Length];
// fs.Read(fileContent,0,(int)fs.Length);
richbox.AppendText("\n開始讀取密文文件......");
//讀取密鑰密文
Encrypt_One = new byte[1152];
//方式一
fs.Read(Encrypt_One,0,1152);
richbox.AppendText("\n讀取加密文件第一部分.....");
//方式二
// Buffer.BlockCopy(fileContent,0,Encrypt_One,0,1152);
//利用接收者的私鑰解密
byte [] RsaDecryptionData = ShareClass.RsaDecrypt(ShareClass.OpenFile("B_PrivateKey.txt"),Encrypt_One);
richbox.AppendText("\n為分解數據解密");
//從解密出來的數組RsaDecryptionData分解出KeyIV(密鑰和向量)和簽名
byte [] KeyIV = new byte[16];
byte [] Signature = new byte[128];
Buffer.BlockCopy( RsaDecryptionData,0,KeyIV,0,16);
Buffer.BlockCopy( RsaDecryptionData,16,Signature,0,128 );
richbox.AppendText("\n分解出會話密鑰和密鑰簽名");
//驗證簽名數據的正確與否
byte [] Key,IV;
if( ShareClass.VerifySignature( ShareClass.OpenFile( "A_PublicKey.txt" ), KeyIV, Signature ) ) //使用共鑰驗證簽名
{//簽名正確,分解密碼和向量
Key = new byte[8];
IV = new byte[8];
Buffer.BlockCopy(KeyIV,0,Key,0,8);
Buffer.BlockCopy(KeyIV,8,IV,0,8);
richbox.AppendText("\n成功得到會話密鑰參數:Key和IV!");
}
else
{
richbox.AppendText("\n密鑰簽名不正確!");
return ;
}
//讀取加密的明文
// fs.Position = 0 ;
int length = (int)fs.Length-1296;// 1152-144 ; //密文的長度AllEncryptedData
Encrypt_Two = new byte[ length ];
//方式一
richbox.AppendText("\n讀取密文部分......");
fs.Position = 1152 ;
fs.Read(Encrypt_Two,0,length);
//方式二
// Buffer.BlockCopy(fileContent,1152,Encrypt_Two,0,length);
//解密明文數據,還原成帶時間戳的明文
byte [] DecryptionPlainText = ShareClass.DecryptData(0,Key,IV,Encrypt_Two);
richbox.AppendText( "\n使用會話密鑰解密密文。" );
//MD5摘要生成
byte [] HashValue = ShareClass.HashData(0,DecryptionPlainText);//還需要和下面的摘要對比//加時間戳明文
richbox.AppendText( "\n為解密數據進行摘要。" );
//讀取摘要數字
Encrypt_Three = new byte[144];
//方式一
richbox.AppendText( "\n讀取摘要數字部分......" );
fs.Position = fs.Length-144 ;
fs.Read( Encrypt_Three,0,144 );
//方式二
// Buffer.BlockCopy(fileContent,fileContent.Length-144,Encrypt_Three,0,144);
//驗證已經簽名過的加時間戳的明文的摘要//驗證摘要的簽名
byte [] PlainTextHash = new byte[16];
byte [] HashSignatrue = new byte[128];
richbox.AppendText( "\n分解摘要數字部分含時間戳明文的摘要和簽名" );
Buffer.BlockCopy(Encrypt_Three,0,PlainTextHash,0,16);
Buffer.BlockCopy(Encrypt_Three,16,HashSignatrue,0,128);
richbox.AppendText("開始對含時間戳明文摘要的簽名進行驗證......");
if( ShareClass.VerifySignature( ShareClass.OpenFile("A_PublicKey.txt"),PlainTextHash,HashSignatrue ) )//驗證明文摘要
{
richbox.AppendText("\n驗證加進時間戳明文的摘要的簽名正確!");
//要進行摘要對比
richbox.AppendText( "\n開始比較兩個含時間戳明文摘要是否相等......" );
if(ShareClass.CompareHash( HashValue,PlainTextHash )==true)
{//兩散列比較相等的話//DecryptionPlainText
richbox.AppendText("\n比較兩個加時間戳明文的摘要成功!");
byte [] TimeStampPart = new byte[167];
richbox.AppendText( "\n提取密文解密后的時間戳部分......" );
Buffer.BlockCopy(DecryptionPlainText,DecryptionPlainText.Length-167,TimeStampPart,0,167);
//提取與驗證時間戳
richbox.AppendText( "\n提取時間戳部分摘要和簽名部分......" );
byte [] HashAndTime = new byte[39];
byte [] DTSignature = new byte[128];
Buffer.BlockCopy(TimeStampPart,0,HashAndTime,0,39);
Buffer.BlockCopy(TimeStampPart,39,DTSignature,0,128);
richbox.AppendText( "\n驗證時間戳簽名......" );
if( ShareClass.VerifySignature( ShareClass.OpenFile("DTSPublicKey.txt"),HashAndTime,DTSignature ) )
{//驗證正確
richbox.AppendText("\n驗證DTS 簽名成功!");
byte [] Time = new byte[23];
Buffer.BlockCopy(HashAndTime,16,Time,0,23);
System.Text.UTF8Encoding enc = new System.Text.UTF8Encoding();
richbox.AppendText("\nDTS 簽名時間(接收文件時間):" + enc.GetString( Time,0,Time.Length ) );
//我們選擇把純明文寫進文件
byte [] PurePlainText = new byte[DecryptionPlainText.Length-167];//純明文的長度
Buffer.BlockCopy(DecryptionPlainText,0,PurePlainText,0,DecryptionPlainText.Length-167);
//判斷文件的名字
string[] namePart = fileName.Split('.');
string fileRealName = namePart[0] + "." + namePart[1] ;//這樣寫有缺陷,還需要判斷 namePart[2]是不是最后一個字符串
ShareClass.WriteFile(fileRealName,PurePlainText);
richbox.AppendText( "\n明文提取成功!\n路徑為:" + fileRealName );
}
else
{
richbox.AppendText("\n驗證DTS 簽名失敗!");
}
}
else
{
richbox.AppendText("\n比較兩個加時間戳明文的摘要失敗!");
}
}
fs.Close();//關閉文件讀取
}
private string OpenFile(string title)
{
OpenFileDialog open = new OpenFileDialog();
open.Title = title ;//比如類似 "請打開你要產生摘要的文件:";
open.Filter = "All File (*.*)|*.*";
string FilePath = null ;
if(open.ShowDialog()==DialogResult.OK)
{
FilePath = open.FileName ;
}
return FilePath ;
}
}
}
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -