一、 原理
目前進行數據加密的方法很多,對數據的保護起到一定的作用。但如果采用固定的密鑰或是密鑰隨數據一起傳送,則均不能達到令人滿意的保密效果。在實踐過程中,我摸索出了一套“請求-應答”模式的隨機密鑰方法,對密碼和數據的保密效果都令人十分滿意。
當客戶端程序啟動並企圖與服務器程序建立連接時,客戶程序從服務器端取得一個由服務器程序產生的隨機字串,系統將以此字串為密鑰來傳送用戶登錄密碼和數據。由於密鑰由服務器程序隨機產生,客戶每次登錄時密鑰均不相同,因此大大減少了密碼被攔截導致數據被竊的可能性。
服務器端可以在遠程數據模塊中引出一個自定義接口,該接口返回一個隨機字串。遠程數據模塊要記錄該字串作為後續處理的密鑰。隨機字串的產生法可以多種多樣,最簡單的方法是用Random()函數產生一個隨機數後再由此數用Format()函數或IntToStr()產生一個字符串。
二、 用戶登錄措施
為了防止程序被非法調試從而洩露密碼,必須將客戶的登錄信息在服務器端處理,也可以專門增加一個安全層負責客戶的登錄。客戶的登錄信息儲存在客戶資料表中,包括用戶名、密碼、權限等信息。
客戶程序登錄時,先調用服務器程序的接口獲得密鑰字串,並用此密鑰對用戶輸入的用戶名和密碼進行加密並向服務器發送登錄信息。加密算法可以是DES算法或其它有效算法。服務器接到登錄信息後,先用先前產生並記錄的隨機密鑰對登錄信息進行解密,再將解密後的信息與存儲的客戶資料表中的信息進行對照,從而判斷客戶信息是否合法以及該客戶享有的數據權限等。
該過程的客戶端程序如下:
strKey:=myRemoteSever.GetKey();
{調用服務器的接口獲得隨機密鑰}
UserName:=Ency(strUserName,strKey);
{對用戶名加密,Ency()為加密算法}
Password:=Ency(strPassword,strKey);
{對登錄密碼進行加密}
If myRemoteServer.LogIn(UserName,Password) then {登錄}
Begin
{進行處理}
End;
服務器端的登錄過程LogIn()如下:
strUserName:=DeEncy(UserName,strKey);
{對用戶名解密,DeEncy()為解密算法}
strPassword:=DeEncy(Password,strKey);
{對登錄密碼解密}
{查詢數據庫}
if (Pass) then
Result:=true
Else
Result:=false;
要注意的是,在服務器程序和客戶程序中,StrKey均應定義為全程變量。
為了防止客戶資料表被程序外打開從而洩露密碼,可以對客戶資料進行一定的加密措施,例如PARADOX表可以添加Password,服務器程序在訪問客戶資料表時先提供該Password。
三、 數據傳送
在網絡程序中,一些敏感數據在網上傳送時必須加密。Delphi的MIDAS機制提供了數據加密的途徑,可以在數據傳往客戶端之前對一些字段進行加密,也可以在接收到客戶端的更新數據請求後對來自客戶端的數據的相應字段進行解密後才向數據庫進行更新。為了達到些目的,可以在服務器程序的遠程數據模塊中加入一個Tprovider或是TdataSetProvider對象,並將此對象的DataSet屬性置為要處理的數據集。在Tprovider的OnGetData事件中加入如下代碼:
with DataSet do
begin
while not EOF do
begin
Edit;
SensitiveData.AsString :=
Ency(SensitiveData.AsString,strKey);
{對敏感數據加密}
Post;
Next;
end;
end;
以上代碼可以將敏感數據加密後再送往客戶程序。
同樣,在Tprovider的OnUpdateData事件中加入一些處理代碼便可對客戶端送來的數據進行解密。
以上只是介紹了網絡程序安全措施實現的一般原理,在此基礎上,可以增加其它保密措施,以達到更好的保密效果。例如,客戶程序可以用特定的輔助硬件設備來增加安全性。在智能卡應用程序中,客戶程序在登錄時不僅要求用戶輸入用戶名和密碼,程序同時檢查IC讀寫器中IC卡的類型及特定的內容,這樣,既使密碼洩露了不會被人冒名登錄。當然,任何安全措施都不是絕對安全的,安全措施還要有嚴格的保密制度及使用人員的高度的保密意識才能真正起到保密作用。