全面保護(hù)你的Java程序安全(上)

字號(hào):

第一部分:Java的安全基礎(chǔ)——虛擬機(jī)和字節(jié)碼安全
    概論:安全問(wèn)題對(duì)很多數(shù)人來(lái)說(shuō)都非常重要。從其歷史看,Java安全主要意味著虛擬機(jī)和字節(jié)碼安全。然而這個(gè)看法忽略了兩個(gè)重要方面—應(yīng)用程序和網(wǎng)絡(luò)安全。在下面一系列文章中,Todd Sundsted講解了JAVA虛擬機(jī)安全,應(yīng)用程序安全,網(wǎng)絡(luò)安全,解釋了應(yīng)該采取什么樣的措施來(lái)全面鞏固你的Java安全。在這第一部分,他向我們解釋了Java安全的基礎(chǔ):虛擬機(jī)和字節(jié)碼安全。
    “似乎還沒(méi)有人曾因?yàn)閷懗隽瞬话踩腏ava代碼而遭解雇”。這句話是我對(duì)那句流行語(yǔ)“沒(méi)人曾因購(gòu)買了IBM而遭解雇”的修正版本。那些更關(guān)心網(wǎng)絡(luò)速度和那些更有興趣為簡(jiǎn)歷添加更多有價(jià)值項(xiàng)目的雇員常常犯下安全問(wèn)題。
    再來(lái)看看另一個(gè)令人擔(dān)心的現(xiàn)象:在我同管理人員和工程技術(shù)人員談?wù)摪踩珕?wèn)題時(shí),我常常發(fā)現(xiàn)他們對(duì)自己的行為存在一些誤解,他們認(rèn)為不必考慮安全問(wèn)題,因?yàn)椤癑ava本身就等于安全”。在這樣錯(cuò)誤觀念的指引下,工程師們沒(méi)有去考慮以下三個(gè)方面的安全問(wèn)題:虛擬機(jī)安全,應(yīng)用程序安全,網(wǎng)絡(luò)安全。
    在以下一系列文章中,我會(huì)盡力修正這種錯(cuò)誤見(jiàn)解。接下來(lái),我將就三方面的問(wèn)題來(lái)對(duì)Java安全進(jìn)行討論,并舉列說(shuō)明一般安全問(wèn)題是怎樣竊入的。另外我也會(huì)介紹一些辦法來(lái)創(chuàng)建安全的應(yīng)用程序。
    ·三種安全問(wèn)題:
    在Java初次露面時(shí),開(kāi)發(fā)者,研究人員,新聞媒體界對(duì)其安全問(wèn)題就反響劇烈。在早前的時(shí)候,Java安全就是意味著字節(jié)碼安全和虛擬機(jī)安全。由于Java過(guò)去主要是作為下載到本地執(zhí)行的小應(yīng)用程序開(kāi)發(fā)語(yǔ)言,下載下來(lái)的代碼的安全性和執(zhí)行環(huán)境就是異常重要的事情。這種情況下的安全意味著正確安裝類裝載器和安全管理器以及驗(yàn)證下載的代碼。
    在我以前開(kāi)發(fā)C/C++程序的數(shù)年里,我從沒(méi)擔(dān)心過(guò)虛擬機(jī)安全問(wèn)題—這個(gè)問(wèn)題完全是隨著Java而成了人們關(guān)注的中心。談到安全問(wèn)題,我擔(dān)心的總是應(yīng)用程序漏洞或是危及程序或系統(tǒng)安全的執(zhí)行情況。在C++領(lǐng)域,應(yīng)用程序上的安全包括限制“setuid”代碼范圍(在Unix環(huán)境,setuid代碼是作為另外的用戶進(jìn)程來(lái)運(yùn)行—典型的情況是超級(jí)用戶)并力圖避免緩沖溢出及其它類型的堆棧問(wèn)題。
    而分布式應(yīng)用程序的引入則帶來(lái)了另外一些方面的問(wèn)題。正如其名字所示,分布式程序由多個(gè)部分組成,每個(gè)部分都駐留在它自己的機(jī)器上,并通過(guò)公共網(wǎng)絡(luò)和其它部分通信。一個(gè)Web應(yīng)用就是典型的列子。在網(wǎng)絡(luò)意義上的安全則意味著簽名,授權(quán),應(yīng)用程序組件,加密通信管道等。
    許多開(kāi)發(fā)人員并不清楚以上幾方面的不同,并以為Java在虛擬機(jī)一層安全了,那么整個(gè)應(yīng)用程序就安全了。我很希望改變這種觀念。下面就開(kāi)始來(lái)討論Java的虛擬機(jī)安全。
    ·安全基礎(chǔ):虛擬機(jī)安全
    虛擬機(jī)安全,長(zhǎng)期以來(lái)一直是開(kāi)發(fā)人員注意的焦點(diǎn),幾乎直到現(xiàn)在也還是沒(méi)有結(jié)果。
    我最初對(duì)討論虛擬機(jī)安全感到有興趣是在轉(zhuǎn)向應(yīng)用程序和網(wǎng)絡(luò)安全之前。我決定給予它同另兩個(gè)部分同樣公平的時(shí)間來(lái)討論,這出于兩個(gè)理由:首先,優(yōu)秀的編程教材因該包含過(guò)去6年來(lái)發(fā)現(xiàn)過(guò)的大量漏洞,第二,很多安全問(wèn)題跨越了我要討論的三個(gè)方面。為了能透徹理解,你必須要全面熟悉三個(gè)方面,包括Java虛擬機(jī)安全。
    如果你檢查過(guò)去6年發(fā)現(xiàn)的各種安全問(wèn)題(看http://www.javaworld.com/javaworld/jw-06-2001/jw-0615-howto.html#resources的官方清單),你將發(fā)現(xiàn)它們被分成一系列目錄。就所關(guān)注的虛擬機(jī)安全來(lái)講,最重要的兩種安全漏洞都是圍繞著未被驗(yàn)證和可能非法的字節(jié)碼以及Java類型系統(tǒng)破壞來(lái)展開(kāi)。在實(shí)際開(kāi)發(fā)中,這兩者經(jīng)常是關(guān)聯(lián)在一起
    ·未驗(yàn)證代碼探秘
    在JVM通過(guò)網(wǎng)絡(luò)從服務(wù)器上下載類代碼時(shí),它并沒(méi)有辦法知道這些字節(jié)碼是否能安全執(zhí)行。安全的字節(jié)碼永不會(huì)指示虛擬機(jī)執(zhí)行讓Java運(yùn)行時(shí)處于不懈調(diào)和無(wú)效的狀態(tài)。
    通常,Java編譯器可以確保創(chuàng)建的類文件里的字節(jié)碼是安全的。然而也可以手工寫出Java編譯器不允許的字節(jié)碼。Java校驗(yàn)器以一系列極富想像力的方法檢查所有這樣的字節(jié)碼并驗(yàn)證那些不合規(guī)范的代碼。一旦校驗(yàn)完成,JVM便知道程序代碼是安全的—只要校驗(yàn)器正常工作。
    下面讓我們來(lái)看看一個(gè)列子,以更好的理解校驗(yàn)器所扮演的角色,并看看一旦校驗(yàn)器失效會(huì)產(chǎn)生什么后果。
    考慮一下下面這個(gè)類:
    public class Test1
    {
    public static void main(String [] arstring)
    {
    Float a = new Float(56.78);
    Integer b = new Integer(1234);
    System.out.println(a.toString());
    }
    }