2. Java的安全模型

Java安全模型側(cè)重于保護終端用戶免受從網(wǎng)絡(luò)下載的净赴、來自不可靠來源的火诸、惡意程序(以及善意程序中的bug)的侵犯该窗。為了達到這個目的酌心,Java提供了一個用戶可配置的“沙箱”拌消,在沙箱中可以放置不可靠的Java程序。

2.1 基本沙箱

沙箱模型使你可以接收來自任何來源的代碼安券,而不是要求用戶避免將來自不受信站點的代碼下載到機器上墩崩。

組成Java沙箱的基本組件如下:

  • 類裝載器結(jié)構(gòu)
  • class文件檢驗器
  • 內(nèi)置于Java虛擬機(及語言)的安全特性
  • 安全管理器及Java API

2.2 類裝載器體系結(jié)構(gòu)

在Java沙箱中,類裝載器是第一道防線:

  • 它防止惡意代碼去干涉善意的代碼
  • 它守護了被信任的類庫的邊界
  • 它將代碼歸入某類(稱為保護域)侯勉,該類確定了代碼可以進行哪些操作

類裝載器體系結(jié)構(gòu)可以防止惡意的代碼去干涉善意的代碼鹦筹,是通過為由不同的類裝載器裝入的類提供不同的命名空間來實現(xiàn)的。命名空間由一系列唯一的名稱組成址貌,每一個被裝載的類有一個名字铐拐,這個命名空間是由Java虛擬機為每一個類裝載器維護的。

圖2-1 類裝載器和命名空間.png

類裝載器體系結(jié)構(gòu)守護了被信任的類庫的邊界练对,是通過分別使用不同的類裝載器裝載可靠的包和不可靠的包來實現(xiàn)的遍蟋。

從Java 1.2版本開始,類裝載器請求另一個用戶自定義類裝載器來裝載一個類型的過程被形式化锹淌,稱為雙親委派模式匿值。除啟動類裝載器外的每一個類裝載器,都有一個“雙親”類裝載器赂摆,在某個特定的類裝載器試圖以常用方式裝載類型之前挟憔,它會先默認地將這個任務(wù)“委派”給它的雙親——請求它的雙親來裝載這個類型钟些。

運行時包,是指由同一個類裝載器裝載的绊谭、屬于同一個包的政恍、多個類型的集合。在允許兩個類型之間對包內(nèi)可見的成員進行訪問前达传,虛擬機不但要確定這兩個類型屬于同一個包篙耗,還必須確認它們屬于同一個運行時包——它們必須是由同一個類裝載器裝載的。

除了屏蔽不同命名空間的類以及保護受信任的類庫的邊界外宪赶,類裝載器還起到了另外的安全作用宗弯。類裝載器必須將每一個被裝載的類放置在一個保護域中,一個保護域定義了這個代碼在運行時將得到怎樣的權(quán)限搂妻。

2.3 class文件檢驗器

和類裝載器一起蒙保,class文件檢驗器保證裝載的class文件內(nèi)容有正確的內(nèi)部結(jié)構(gòu),并且這些class文件相互間協(xié)調(diào)一致欲主。如果class文件檢驗器在class文件中發(fā)現(xiàn)了問題邓厕,它會拋出異常。

JVM的class文件檢驗器只在字節(jié)碼執(zhí)行之前進行一次分析扁瓢,需要進行四趟獨立的掃描:

  • 第一趟是在類被裝載時進行的详恼,主要檢查class文件的內(nèi)部結(jié)構(gòu)
  • 第二趟和第三趟是在連接過程中進行的,主要確認類型數(shù)據(jù)遵從Java編程語言的語義引几,包括檢驗它所包含的所有字節(jié)碼的完整性昧互。
  • 第四趟是在動態(tài)連接的過程中解析符號時進行的,主要確認被引用的類她紫、字段以及方法確實存在硅堆。

2.4 JVM中內(nèi)置的安全特性

JVM在執(zhí)行字節(jié)碼時還進行其他一些內(nèi)置的安全機制的操作屿储,包括:

  • 類型安全的引用轉(zhuǎn)換
  • 結(jié)構(gòu)化的內(nèi)存訪問(無指針算法)
  • 自動垃圾收集(不必顯式地釋放被分配的內(nèi)存)
  • 數(shù)組邊界檢查
  • 空引用檢查

2.5 安全管理器和Java API

Java安全模型的前三個組成部分——類裝載器體系結(jié)構(gòu)贿讹、class文件檢驗器以及Java中內(nèi)置的安全特性——一起達到一個共同的目的:保持JVM的實例和它正在運行的應(yīng)用程序的內(nèi)部完整性,使得它們不被下載的惡意或有漏洞的代碼侵犯够掠。相反民褂,這個安全模型的第四個組成部分是安全管理器,它主要用于保護虛擬機的外部資源不被虛擬機內(nèi)運行的惡意或有漏洞的代碼侵犯疯潭。

安全管理器定義了沙箱的外部邊界赊堪。因為它是可定制的,所以它允許為程序建立自定義的安全策略竖哩。

Java應(yīng)用程序在啟動時不會默認安裝安全管理器哭廉,也不會有任何安全限制。在Java 1.2版本以前相叁,如果安裝了安全管理器遵绰,那么它將負責(zé)應(yīng)用程序整個剩余的生命周期辽幌,不能被替代、擴展或者修改椿访。在1.2版本中乌企,當(dāng)前安裝的安全管理器能夠在允許的情況下被替換。

安全管理器主要負責(zé)兩個方面的工作:說明一個安全策略以及執(zhí)行這個安全策略成玫。

Java 1.2版本中的java.lang.SecurityManager是一個具體的類加酵,它提供了一個默認的安全管理器的實現(xiàn),能夠輔助建立一個基于代碼簽名的細粒度的安全策略哭当。用戶可以顯示實例化這個安全管理器猪腕,或者讓它自動安裝。例如钦勘,在Sun的Java 2 SDK版本1.2中码撰,可以在命令行使用-Djava.security.manager選項來指明安裝具體安全管理器。

具體安全管理器類允許用戶不用Java代碼定義自己的安全策略个盆,而是用一個稱為策略文件的ASCII文件脖岛。在策略文件中,可以給代碼來源授予權(quán)限颊亮。權(quán)限是用類定義的柴梆,它是java.security.Permission的子類。代碼來源是由代碼庫的URL和一些簽名組成的终惑,從這個URL可以裝載代碼绍在,而簽名則為這個代碼作擔(dān)保。當(dāng)創(chuàng)建安全管理器時雹有,它對策略文件進行解析偿渡,并創(chuàng)建CodeSource(代碼來源)和Permission(權(quán)限)對象,這些對象被封裝在一個單獨的Policy對象中霸奕,這個Policy對象就代表了運行時的策略溜宽。任何時刻只能有一個Policy對象被安裝。

類裝載器將類型放到保護域(ProtectionDomain)中质帅,保護域封裝了授予代碼來源的所有權(quán)限适揉,這些代碼來源由裝載的類型代表。

當(dāng)具體安全管理器的check方法被調(diào)用時煤惩,它們中的大多數(shù)都將請求傳遞給一個稱為AcessController的類嫉嘀。這個AccessController使用了包含在保護域?qū)ο笾械男畔ⅲ@個對象所屬的類的方法在調(diào)用棧中魄揉,AccessController進行棧檢查以確定這個操作能否被執(zhí)行剪侮。

java.lang.SecurityManager中有兩個關(guān)鍵方法:

  • checkPermission(Permission perm) —— 進行某個操作(它需要指定的權(quán)限)前被調(diào)用
  • checkPermission(Permission perm, Object context) —— 在被傳遞的安全上下文中進行某個操作(它需要指定的權(quán)限)前被調(diào)用

在具體安全管理器類中,checkPermission( )方法同樣負責(zé)決定洛退,是否允許將某個操作的任務(wù)委派給另一個方法瓣俯。這個checkPermission( )方法只是簡單地調(diào)用了類java.security.AccessController中的靜態(tài)checkPermission( )方法红淡,并將這個Permission對象傳遞給它。

2.6 代碼簽名和認證

Java安全模型很重要的一點就是它支持認證降铸。認證可以使用戶確認在旱,由某些團體擔(dān)保的一些class文件是值得信任的,并且這些class文件在到達用戶虛擬機的途中沒有被改變推掸。這樣桶蝎,如果用戶在一定程度上信任這個為代碼作擔(dān)保的團體,也就可以在一定程度上簡化沙箱對這段代碼的限制谅畅〉窃可以對由不同團體簽名的代碼建立不同的安全限制。

圖2-2 對一個jar文件簽名.png
圖2-3 對一個已簽名的jar文件驗簽.png

2.7 策略

Java安全體系結(jié)構(gòu)的真正好處在于毡泻,它可以對代碼授予不同層次的信任度來部分地訪問系統(tǒng)胜茧。

版本1.2的安全體系結(jié)構(gòu)的主要目標之一就是使建立(以代碼簽名為基礎(chǔ)的)細粒度的訪問控制策略的過程更為簡單且更少出錯。在版本1.2的安全模型中仇味,權(quán)限(系統(tǒng)訪問權(quán)限)使授予代碼來源的呻顽。

對應(yīng)于整個Java應(yīng)用程序的一個訪問控制策略是由抽象類java.security.Policy的一個子類的單個實例所表示的。在任何時候丹墨,每個應(yīng)用程序?qū)嶋H上都只有一個Policy對象廊遍。類裝在其利用這個Policy對象來幫助它們決定,在把一段代碼導(dǎo)入虛擬機時應(yīng)該給它們怎么樣的權(quán)限贩挣。

安全策略是一個從描述運行代碼的屬性集合到這段代碼所擁有的權(quán)限的映射喉前。在版本1.2的安全體系結(jié)構(gòu)中,描述運行代碼的屬性被總稱為代碼來源王财。

在版本1.2中卵迂,所有和具體安全管理器有關(guān)的工具和訪問控制體系結(jié)構(gòu)都只對證書起作用,而不能對“赤裸”的公鑰起作用绒净。

權(quán)限是由抽象類java.security.Permission的一個子類的實例表示的见咒。一個Permission對象有三個屬性:類型、名字和可選的操作疯溺。

在Policy對象中论颅,每一個CodeSource是和一個或多個Permission對象相關(guān)聯(lián)的。

策略文件

由Sun提供的在Java 1.2平臺下的具體Policy子類采用如下方法:在一個ASCII策略文件中用上下文無關(guān)文法描述安全策略囱嫩。

keystore "ijvmkeys";

grant signedBy "friend" {
    permission java.io.FilePermission "question.txt", "read";
    permission java.io.FilePermission "answer.txt", "read";
};

grant signedBy "stranger" {
    permission java.io.FilePermission "question.txt", "read";
};

grant codeBase "file:${com.artima.ijvm.cdrom.home}/security/ex2/*" {
    permission java.io.FilePermission "question.txt", "read";
    permission java.io.FilePermission "answer.txt", "read";
};

最后一條grant語句中的代碼庫URL采用了文件的形式:它包含了一個屬性${com.artima.ijvm.cdrom.home}

2.8 保護域

當(dāng)類裝載器將類型裝入JVM時漏设,它們將為每個類型指派一個保護域墨闲。保護域定義了授予一段特定代碼的所有權(quán)限。(一個保護域?qū)?yīng)于策略文件中的一個或多個grant子句郑口。)裝載入JVM的每一個類型都屬于且僅屬于一個保護域鸳碧。

雖然前面的Policy對象代表了一個從代碼來源到權(quán)限的全局映射盾鳞,但是最終還是由類裝載器負責(zé)決定代碼執(zhí)行時將獲得怎樣的權(quán)限。

圖2-4用圖形化的方式描述了保護域瞻离、代碼來源以及權(quán)限腾仅。ProtectionDomain對象封裝了一個到CodeSource對象的引用以及一個到java.security.Permissions對象的引用。java.security.Permissions是抽象類java.security.PermissionCollection的一個具體類套利,代表了一個同構(gòu)權(quán)限的集合推励。

圖2-4 保護域、代碼來源以及權(quán)限.png

當(dāng)一個類裝載器將Friend和Friend$1導(dǎo)入方法區(qū)時肉迫,類裝載器將把一個ProtectionDomain對象的引用和這些class文件的字節(jié)傳遞給defineClass( )方法验辞。這個defineClass( )方法將Friend和Friend$1所在的方法區(qū)中的類型數(shù)據(jù)和被傳遞的ProtectionDomain對象相關(guān)聯(lián)。

2.9 訪問控制器

java.security.AccessController提供了一個默認的安全策略執(zhí)行機制喊衫,它使用棧檢查來決定潛在不安全的操作是否被允許跌造。

由AccessController的checkPermission( )實現(xiàn)的基本算法決定了調(diào)用棧中的每個幀是否有權(quán)執(zhí)行潛在不安全的操作。每一個棧幀代表了由當(dāng)前線程調(diào)用的某個方法族购,每一個方法是在某個類中定義的壳贪,每一個類又屬于某個保護域,每個保護域包含一些權(quán)限寝杖。因此撑碴,每個棧幀間接地和一些權(quán)限相關(guān)。

當(dāng)調(diào)用doPrivileged( )方法時朝墩,就像調(diào)用其它任何方法一樣醉拓,都會將一個新的棧幀壓入棧。在由AccessController執(zhí)行的棧檢查中收苏,一個doPrivileged( )方法調(diào)用的棧幀標識了檢查過程的提前終止點亿卤。如果和調(diào)用doPrivileged( )的方法相關(guān)聯(lián)的保護域擁有執(zhí)行被請求操作的權(quán)限,AccessController將立即返回鹿霸。這樣這個操作就被允許排吴,即使在棧下層的代碼可能沒有執(zhí)行這個操作的權(quán)限。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末懦鼠,一起剝皮案震驚了整個濱河市钻哩,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌肛冶,老刑警劉巖街氢,帶你破解...
    沈念sama閱讀 216,692評論 6 501
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異睦袖,居然都是意外死亡珊肃,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,482評論 3 392
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來伦乔,“玉大人厉亏,你說我怎么就攤上這事×液停” “怎么了爱只?”我有些...
    開封第一講書人閱讀 162,995評論 0 353
  • 文/不壞的土叔 我叫張陵,是天一觀的道長招刹。 經(jīng)常有香客問我恬试,道長,這世上最難降的妖魔是什么蔗喂? 我笑而不...
    開封第一講書人閱讀 58,223評論 1 292
  • 正文 為了忘掉前任忘渔,我火速辦了婚禮,結(jié)果婚禮上缰儿,老公的妹妹穿的比我還像新娘畦粮。我一直安慰自己,他們只是感情好乖阵,可當(dāng)我...
    茶點故事閱讀 67,245評論 6 388
  • 文/花漫 我一把揭開白布宣赔。 她就那樣靜靜地躺著,像睡著了一般瞪浸。 火紅的嫁衣襯著肌膚如雪儒将。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,208評論 1 299
  • 那天对蒲,我揣著相機與錄音钩蚊,去河邊找鬼。 笑死蹈矮,一個胖子當(dāng)著我的面吹牛砰逻,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播泛鸟,決...
    沈念sama閱讀 40,091評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼蝠咆,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了北滥?” 一聲冷哼從身側(cè)響起刚操,我...
    開封第一講書人閱讀 38,929評論 0 274
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎再芋,沒想到半個月后菊霜,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,346評論 1 311
  • 正文 獨居荒郊野嶺守林人離奇死亡祝闻,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,570評論 2 333
  • 正文 我和宋清朗相戀三年占卧,在試婚紗的時候發(fā)現(xiàn)自己被綠了遗菠。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片联喘。...
    茶點故事閱讀 39,739評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡华蜒,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出豁遭,到底是詐尸還是另有隱情叭喜,我是刑警寧澤,帶...
    沈念sama閱讀 35,437評論 5 344
  • 正文 年R本政府宣布蓖谢,位于F島的核電站捂蕴,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏闪幽。R本人自食惡果不足惜啥辨,卻給世界環(huán)境...
    茶點故事閱讀 41,037評論 3 326
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望盯腌。 院中可真熱鬧溉知,春花似錦、人聲如沸腕够。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,677評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽帚湘。三九已至玫荣,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間大诸,已是汗流浹背捅厂。 一陣腳步聲響...
    開封第一講書人閱讀 32,833評論 1 269
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留资柔,地道東北人焙贷。 一個月前我還...
    沈念sama閱讀 47,760評論 2 369
  • 正文 我出身青樓,卻偏偏與公主長得像建邓,于是被迫代替她去往敵國和親两残。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 44,647評論 2 354

推薦閱讀更多精彩內(nèi)容

  • 1. Java基礎(chǔ)部分 基礎(chǔ)部分的順序:基本語法忌栅,類相關(guān)的語法锄贼,內(nèi)部類的語法,繼承相關(guān)的語法注簿,異常的語法契吉,線程的語...
    子非魚_t_閱讀 31,624評論 18 399
  • (一)Java部分 1、列舉出JAVA中6個比較常用的包【天威誠信面試題】 【參考答案】 java.lang;ja...
    獨云閱讀 7,101評論 0 62
  • 時差黨诡渴,美高生捐晶,坐標加州菲语。 喜歡看書和寫作,酷愛風(fēng)花雪月惑灵。 悲觀主義者山上,周期性焦慮。 對股市感興趣英支。未來打算去念經(jīng)...
    眠舊時書閱讀 234評論 0 0
  • 寫不出東西的我 腦子一片混沌 像被關(guān)在一個封閉的大房子 四面的墻上涂滿了白漆 我盤坐在最中央 窒息感佩憾,孤獨感 充斥...
    做個作家夢閱讀 296評論 0 1
  • 2017年妄帘,對我而言,是一個悲喜交織的年份池凄,悲的是抡驼,我的父親在今年夏天突然離世,我成了沒有雙親的人肿仑,父母在致盟,人生尚...
    快樂英子閱讀 209評論 1 5