黄色网页视频 I 影音先锋日日狠狠久久 I 秋霞午夜毛片 I 秋霞一二三区 I 国产成人片无码视频 I 国产 精品 自在自线 I av免费观看网站 I 日本精品久久久久中文字幕5 I 91看视频 I 看全色黄大色黄女片18 I 精品不卡一区 I 亚洲最新精品 I 欧美 激情 在线 I 人妻少妇精品久久 I 国产99视频精品免费专区 I 欧美影院 I 欧美精品在欧美一区二区少妇 I av大片网站 I 国产精品黄色片 I 888久久 I 狠狠干最新 I 看看黄色一级片 I 黄色精品久久 I 三级av在线 I 69色综合 I 国产日韩欧美91 I 亚洲精品偷拍 I 激情小说亚洲图片 I 久久国产视频精品 I 国产综合精品一区二区三区 I 色婷婷国产 I 最新成人av在线 I 国产私拍精品 I 日韩成人影音 I 日日夜夜天天综合

深入理解Flash的沙箱 – Security Domains-1

系統(tǒng) 3185 0
轉(zhuǎn)載來(lái)自 http://kevincao.com/category/develop/

今天終于有時(shí)間把 senocular 上關(guān)于安全域和應(yīng)用程序域的教程好好看了一遍。覺得人家老外就是專業(yè):內(nèi)容非常有條理且完整,圖文并茂,舉例也非常實(shí)用,真是教程中的精品。剛好我最近也在整理這方面的知識(shí),于是決定把這篇翻譯出來(lái),方便國(guó)內(nèi)的讀者。對(duì)想要進(jìn)階理解Flash的運(yùn)行機(jī)制的朋友,本文是不可多得的好材料。

原文地址: http://www.senocular.com/flash/tutorials/contentdomains/

簡(jiǎn)介

如果你還沒有與復(fù)雜的的安全域(security domain)和應(yīng)用程序域(application domain)問(wèn)題打過(guò)交道,那么你真是個(gè)幸運(yùn)的家伙。當(dāng)你在加載外部?jī)?nèi)容(然后他們開始播放)的時(shí)候,默認(rèn)的設(shè)置工作的很好,你甚至不知道他們的存在。
但是某些時(shí)候你可能需要控制默認(rèn)設(shè)置以外的更多行為和功能,這樣你就會(huì)遇到前面所說(shuō)的問(wèn)題。你也許會(huì)困擾于Security.allowDomain和crossdomain.xml文件的區(qū)別,又或者你想要深究關(guān)于安全性的最佳實(shí)踐。如果是這樣,那么這篇文章就是你所需要的了。
以下的教程將會(huì)討論什么是安全域和應(yīng)用程序域,以及他們?cè)贔lash Player中應(yīng)該如何使用。

安全域

Sandboxing 沙箱

沙箱是用于區(qū)分不同的數(shù)據(jù)和程序執(zhí)行。沙箱對(duì)于安全性尤其重要。如果沒有恰當(dāng)?shù)男湃问跈?quán),兩個(gè)位于不同沙箱內(nèi)的內(nèi)容應(yīng)該沒有任何交互。Flash Player的安全模型使用稱為 安全域 的沙箱來(lái)分離內(nèi)容。
雖然安全性是沙箱的主要用途,但這并不是唯一使用沙箱的原因。另外一種可能的情形是使用沙箱來(lái)避免命名沖突,這種區(qū)分代碼的沙箱方式在Flash Player中被稱為 應(yīng)用域 。

Security Domains 安全域

安全域在Flash中是頂級(jí)的沙箱。安全域鏈接到內(nèi)容的來(lái)源域名,或者是被加載的內(nèi)容(如SWF文件)的來(lái)源域名。比如在senocular.com下的SWF文件包含一個(gè)鏈接到senocular.com的安全域,而在example.com下的SWF文件則有一個(gè)鏈接到example.com的安全域。不同的安全域使得SWF文件在Flash Player中播放時(shí)運(yùn)行在自身的沙箱下。

security domains
Flash Player中的安全域沙箱

注意:在本教程的例子中,你將看到我用統(tǒng)一頂級(jí)域名下的不同子域來(lái)代表不同域名,這是因?yàn)樵贔lash中,不同子域和不同頂級(jí)域一樣,都被視為不同的域。示例中代碼也被簡(jiǎn)化過(guò)了,在Flash編輯環(huán)境下用時(shí)間線代碼也可以進(jìn)行測(cè)試。

不可執(zhí)行的內(nèi)容(非SWF文件),比如圖片或者文本文件,也被劃分到安全域中,同樣與他們所處的域名相關(guān)聯(lián)。實(shí)際上,正是域名決定了這些內(nèi)容是否能夠被某個(gè)SWF文件加載。更多這方面的內(nèi)容將在 不可執(zhí)行文件的信任機(jī)制 章節(jié)中進(jìn)行討論。

回到SWF上來(lái),安全域劃分了數(shù)據(jù)和可執(zhí)行代碼。如果兩個(gè)SWF處于不同的安全域下,某個(gè)SWF中的數(shù)據(jù)(比如某個(gè)變量)是不可以被其他SWF獲取的,當(dāng)然,代碼也不能執(zhí)行。如果嘗試獲取其他域中SWF文件的數(shù)據(jù)將會(huì)產(chǎn)生一個(gè)安全錯(cuò)誤。

下面的代碼展示了一個(gè)SWF文件企圖加載另外一個(gè)SWF,并獲取其文檔類的實(shí)例(也就是主時(shí)間線)。

http://same.example.com/parent.swf:

        
          var
        
         loader:Loader = 
        
          new
        
         Loader
        
          (
        
        
          )
        
        ;
loader.
        
          contentLoaderInfo
        
        .
        
          addEventListener
        
        
          (
        
        Event.
        
          INIT
        
        , init
        
          )
        
        ;


        
          var
        
        
          url
        
        :
        
          String
        
         = 
        
          "http://diff.example.com/child.swf"
        
        ;
loader.
        
          load
        
        
          (
        
        
          new
        
         URLRequest
        
          (
        
        
          url
        
        
          )
        
        
          )
        
        ; 


        
          function
        
         init
        
          (
        
        event:Event
        
          )
        
        :
        
          void
        
        
          {
        
        
          trace
        
        
          (
        
        loader.
        
          content
        
        
          )
        
        ;
	
        
          // SecurityError: Error #2121: Security sandbox violation:
        
        
          // Loader.content: http://same.example.com/parent.swf
        
        
          // cannot access http://diff.example.com/child.swf.
        
        
          // This may be worked around by calling Security.allowDomain.
        
        
          }
        
      

任意想要獲取被加載的SWF文件的內(nèi)容的嘗試,甚至包括trace Loader的content屬性。都會(huì)引起安全錯(cuò)誤,因?yàn)樗麄儍烧咛幱诓煌陌踩騼?nèi)。

安全域的劃分也適用于Flash Player所使用的原生ActionScript類。Flash Player在每個(gè)安全域中都創(chuàng)建了獨(dú)立的原生類。舉例來(lái)說(shuō),一個(gè)安全域內(nèi)的XML類與另外一個(gè)安全域內(nèi)的XML類是不相同的,改變其中一個(gè)XML的靜態(tài)屬性XML.prettyIndent并不會(huì)影響到另一個(gè)安全域。

下面這個(gè)SWF文件加載了兩個(gè)子SWF,一個(gè)來(lái)自自身的域,另一個(gè)從另外的域加載。我們改變了主文件的prettyIndent屬性,來(lái)看看這兩個(gè)子文件的屬性輸出。

http://same.example.com/parent.swf:

        
          trace
        
        
          (
        
        
          XML
        
        .
        
          prettyIndent
        
        
          )
        
        ; 
        
          // 2
        
        
          XML
        
        .
        
          prettyIndent
        
         = 
        
          5
        
        ;

        
          trace
        
        
          (
        
        
          XML
        
        .
        
          prettyIndent
        
        
          )
        
        ; 
        
          // 5
        
        
          // Same domain:
        
        
          var
        
         sameLoader:Loader = 
        
          new
        
         Loader
        
          (
        
        
          )
        
        ;

        
          var
        
         sameURL:
        
          String
        
         = 
        
          "http://same.example.com/child.swf"
        
        ;
sameLoader.
        
          load
        
        
          (
        
        
          new
        
         URLRequest
        
          (
        
        sameURL
        
          )
        
        
          )
        
        ; 


        
          // Different domain:
        
        
          var
        
         diffLoader:Loader = 
        
          new
        
         Loader
        
          (
        
        
          )
        
        ;

        
          var
        
         diffURL:
        
          String
        
         = 
        
          "http://diff.example.com/child.swf"
        
        ;
diffLoader.
        
          load
        
        
          (
        
        
          new
        
         URLRequest
        
          (
        
        diffURL
        
          )
        
        
          )
        
        ;
      

http://same.example.com/child.swf:

        
          trace
        
        
          (
        
        
          "same: "
        
         + 
        
          XML
        
        .
        
          prettyIndent
        
        
          )
        
        ; 
        
          // same: 5
        
      

http://diff.example.com/child.swf:

        
          trace
        
        
          (
        
        
          "diff: "
        
         + 
        
          XML
        
        .
        
          prettyIndent
        
        
          )
        
        ; 
        
          // diff: 2
        
      

可以看到,第二個(gè)子文件的屬性并沒有被改變。這就說(shuō)明不同的安全域具有不同的原生ActionScript類定義。

Trust 信任授權(quán)

盡管安全域只允許相同域下的通訊,但是我們可以通過(guò)信任授權(quán)來(lái)讓處于兩個(gè)不同安全域內(nèi)的SWF文件進(jìn)行通訊。通過(guò)授權(quán),某個(gè)安全域內(nèi)的文件可以獲取另一個(gè)域內(nèi)文件的的數(shù)據(jù),或者調(diào)用其方法,就像是處于相同的安全域下一樣。

在ActionScript中,SWF的信任授權(quán)是通過(guò) Security.allowDomain (或者類似的 Security.allowInsecureDomain )來(lái)設(shè)置的。在被信任的安全域內(nèi)的代碼可以調(diào)用這個(gè)方法來(lái)授權(quán)信任給另一個(gè)或者一組在其他安全域內(nèi)的SWF文件。這種信任是單向的,發(fā)起allowDomain的SWF文件不能去訪問(wèn)被授權(quán)信任的文件,除非對(duì)方也做了信任授權(quán)。

Security domains with trust
建立信任關(guān)系的安全域

在下面的例子中,一個(gè)子SWF文件調(diào)用allowDomain來(lái)允許父SWF的訪問(wèn):

http://home.example.com/parent.swf:

        
          var
        
         loader:Loader = 
        
          new
        
         Loader
        
          (
        
        
          )
        
        ;
loader.
        
          contentLoaderInfo
        
        .
        
          addEventListener
        
        
          (
        
        Event.
        
          INIT
        
        , init
        
          )
        
        ;


        
          var
        
        
          url
        
        :
        
          String
        
         = 
        
          "http://away.example.com/child.swf"
        
        ;
loader.
        
          load
        
        
          (
        
        
          new
        
         URLRequest
        
          (
        
        
          url
        
        
          )
        
        
          )
        
        ;


        
          function
        
         init
        
          (
        
        event:Event
        
          )
        
        :
        
          void
        
        
          {
        
        
          // (子文件執(zhí)行了allowDomain)
        
        
          trace
        
        
          (
        
        loader.
        
          content
        
        
          )
        
        ; <em>
        
          // [object DocumentClass]</em>
        
        
          }
        
      

http://away.example.com/child.swf:

        Security.
        
          allowDomain
        
        
          (
        
        
          "home.example.com"
        
        
          )
        
        ;
      

如果沒有授信,就像前文說(shuō)到的,還是會(huì)引發(fā)安全錯(cuò)誤。但是一旦被加載的子SWF調(diào)用了allowDomain以后,父SWF文件就可以自由的訪問(wèn)子SWF文件中的內(nèi)容。要注意的是在這個(gè)例子中,由于父SWF文件沒有授權(quán)away.example.com的信任,所以子SWF仍然無(wú)法訪問(wèn)loader的content屬性。

信任是非常重要的安全概念,絕對(duì)不能掉以輕心。我們經(jīng)??匆娛褂猛ㄅ浞氖跈?quán):

        
          // 小心哦!
        
        
Security.
        
          allowDomain
        
        
          (
        
        
          "*"
        
        
          )
        
        ;
      

這么做將允許所有SWF文件,不僅僅只是你加載的或是加載你的,可以通過(guò)ActionScript來(lái)訪問(wèn)你文件中的數(shù)據(jù)。就算你沒有在文件中包含敏感數(shù)據(jù),但是如果你在文件中提供了某些方法去獲取這種數(shù)據(jù),那也有可能被其他SWF調(diào)用。使用allowDomain來(lái)授權(quán)的信任就像給了其他SWF文件相等的權(quán)利:你能做什么,我就能做什么。在接下來(lái)的 合并安全域 章節(jié)中你將看到這意味著什么。

如果你只是想讓SWF之間能夠通信,除了信任授權(quán)的方法以外我們還可以使用sharedEvents對(duì)象來(lái)實(shí)現(xiàn),我們將在 在非受信的SWF之間通訊 章節(jié)中討論。

Non-executable Trust 不可執(zhí)行文件的信任機(jī)制

由于不可執(zhí)行文件(也就是非SWF文件)不能調(diào)用allowDomain代碼,所以這類文件的信任機(jī)制在Flash Player中有不一樣的處理方法。這就是跨域(cross-domain)策略文件派上用場(chǎng)的地方。

跨域策略文件是一個(gè)放在網(wǎng)站的根域名下的命名為crossdomain.xml的XML文件。和allowDomain類似,定義了一組可以被Flash Player加載的安全網(wǎng)站域名。一個(gè)簡(jiǎn)單的跨域策略文件的例子如下:

http://example.com/crossdomain.xml:

        <?xml version="1.0"?>
<cross-domain-policy>
	<site-control permitted-cross-domain-policies="by-content-type"/>
	<allow-access-from domain="*.example.com"/>
	<allow-access-from domain="www.example-partner.com"/>
</cross-domain-policy>
      

你可以從 Cross-domain policy file specification (adobe.com)獲得詳細(xì)的文件格式信息。

和allowDomain不同的是,跨域策略文件只提供了包含所有文件(通常是一個(gè)域下的所有文件)的用法。上面的例子表示允許來(lái)自example.com的任意子域或www.example-partner.com的SWF文件加載example.com下的文件。

由于存在allowDomain機(jī)制,跨域策略文件通常不用于授權(quán)SWF文件的訪問(wèn)??缬蚣虞dSWF的時(shí)候不會(huì)請(qǐng)求跨域策略文件。只有當(dāng)要把一個(gè)跨域的SWF合并到當(dāng)前的安全域的時(shí)候,才需要提供跨域策略文件。這個(gè)主題將在 合并安全域 中進(jìn)行討論。

不管是標(biāo)準(zhǔn)的位于域名根目錄下的跨域策略文件還是用 Security.loadPolicyfile 指定的跨域策略文件,都只有在需要的時(shí)候才會(huì)被加載:當(dāng)內(nèi)容被加載的同時(shí),跨域策略文件也被一起加載進(jìn)來(lái)。

加載完成后,F(xiàn)lash Player分析跨越策略文件并判斷該域是否為信任SWF所處的域。如果答案是肯定的話,文件正常加載,就像處于和SWF文件相同的域一樣。反之則有可能有兩種情況:

  • 文件不被加載
  • 文件加載成功,但是其數(shù)據(jù)不能被SWF文件直接訪問(wèn)

如果文件本身就是數(shù)據(jù)(文本文件,XML文件,二進(jìn)制數(shù)據(jù)等等),那么文件就不會(huì)被加載。

Policy file for loading

需要跨域策略文件來(lái)加載僅包含數(shù)據(jù)的文件

如果文件除了數(shù)據(jù)以外還有其余用途(圖像文件,聲音文件等),那么文件還是能夠被加載到用戶可見(可聽)的環(huán)境中。比如說(shuō)圖像文件,就算沒有跨域策略文件,還是可以在Loader對(duì)象中顯示給用戶看。但是類似BitmapData.draw等直接訪問(wèn)圖像數(shù)據(jù)的方法就不能運(yùn)行。

Policy file for trusting

需要跨域策略文件來(lái)獲取其他文件的數(shù)據(jù)的引用

對(duì)此可能大家都有點(diǎn)疑惑。實(shí)際上用戶是可以訪問(wèn)這些數(shù)據(jù)的,但是SWF文件不行。Flash Player是在保護(hù)用戶的數(shù)據(jù)不被潛藏有危險(xiǎn)代碼的SWF文件獲取。用戶不需要關(guān)心跨域策略文件也能正常的瀏覽網(wǎng)頁(yè)內(nèi)容。

但這并不是說(shuō)跨域策略文件可以被忽視,類似于下面這種過(guò)分縱容的跨域策略文件有很多潛在的危險(xiǎn):

        <?xml version="1.0"?>
<cross-domain-policy>
	
        
          <!-- 
          
            小心哦!
          
           -->
        
        
	<allow-access-from domain="*"/>
</cross-domain-policy>
      

警告 :使用通配符(*)允許所有域的訪問(wèn)等同于: 用戶可能可以接觸到的所有處于該域下的數(shù)據(jù)都有可能被任意SWF文件獲取 。

客戶端的Flash Player運(yùn)行在當(dāng)前用戶的認(rèn)證下,這就表示用戶的數(shù)據(jù)可能就是Flash Player的數(shù)據(jù)。而且Flash Player的數(shù)據(jù)可能被任意在里面運(yùn)行的SWF獲取。Flash Player默認(rèn)只允許相同域名下的SWF的安全數(shù)據(jù),并限制跨域SWF的運(yùn)行。如果沒有這層限制,SWF可以獲取任意當(dāng)前用戶可以獲取的數(shù)據(jù)。

舉個(gè)例子:某用戶使用他的認(rèn)證來(lái)登錄網(wǎng)頁(yè)的郵件客戶端收取郵件,然后用戶打開了一個(gè)包含有惡意程序的SWF的頁(yè)面。如果沒有跨域限制的話,這個(gè)SWF可以用他現(xiàn)有的認(rèn)證偷偷地加載用戶的郵件頁(yè)面。用戶可以訪問(wèn)的內(nèi)網(wǎng)也不例外,只要用戶能去的地方,SWF就能去。幸好Flash Player阻止了這種獲取數(shù)據(jù)的行為,除非該域通過(guò)跨域策略文件給予SWF授權(quán)。

記住一個(gè)原則,永遠(yuǎn)不要對(duì)包含敏感數(shù)據(jù)的域開發(fā)跨域授權(quán),即使需要上面的信息來(lái)進(jìn)行用戶認(rèn)證。把SWF可以訪問(wèn)的數(shù)據(jù)劃分到不同的域或者子域下面。

Domain Description Policy file
login.example.com Hosts user data None
feed.example.com Hosts public data Includes: <allow-access-from domain="*" />

這將使得敏感數(shù)據(jù)不可被訪問(wèn),但是仍然可以對(duì)其他域下的SWF文件公開你的其他數(shù)據(jù)。

Non-executable Content Without Trust 非受信的不可執(zhí)行文件

如果沒有跨域策略文件的信任授權(quán),F(xiàn)lash Player禁止非SWF文件的獲取。特別是像文本那樣的僅包含數(shù)據(jù)的文件,甚至不會(huì)加載。如果你需要從一個(gè)沒有跨域授權(quán)的域中獲取數(shù)據(jù),還是有一個(gè)變通的辦法。

跨域策略文件用于保護(hù)數(shù)據(jù),特別是保護(hù)用戶數(shù)據(jù),或者說(shuō)是用戶能夠接觸到的數(shù)據(jù)。因?yàn)镕lash Player是運(yùn)行在客戶端的,但是服務(wù)器端的代碼沒有這種限制。服務(wù)器完全是另外一臺(tái)機(jī)器,所以用戶請(qǐng)求和服務(wù)器請(qǐng)求是完全無(wú)關(guān)的。

由于服務(wù)器沒有用戶的限制,服務(wù)器端的代碼可以從任意公開的網(wǎng)絡(luò)服務(wù)獲取數(shù)據(jù)。也就是說(shuō)包含SWF的服務(wù)器可以用于訪問(wèn)外部域的數(shù)據(jù),然后作為相同域的數(shù)據(jù)返回給Flash Player。由于處在相同的域下,F(xiàn)lash Player就不需要有跨域策略文件了。

下面的代碼演示了一個(gè)服務(wù)器端的php腳本加載外部數(shù)據(jù)的例子:

http://home.example.com/loader.swf:

        
          var
        
         urlLoader:URLLoader = 
        
          new
        
         URLLoader
        
          (
        
        
          )
        
        ;


        
          var
        
         urlVariables:URLVariables = 
        
          new
        
         URLVariables
        
          (
        
        
          )
        
        ;

        
          // 服務(wù)器端獲取外部數(shù)據(jù)的地址
        
        
urlVariables.
        
          externalURL
        
         = 
        
          "http://away.example.com/content.txt"
        
        ;


        
          // 服務(wù)器端的腳本獲取外部數(shù)據(jù)并傳給SWF
        
        
          var
        
         serverPage:
        
          String
        
         = 
        
          "http://home.example.com/read.php"
        
        ;


        
          var
        
         request:URLRequest = 
        
          new
        
         URLRequest
        
          (
        
        serverPage
        
          )
        
        ;
request.
        
          data
        
         = urlVariables;
urlLoader.
        
          load
        
        
          (
        
        request
        
          )
        
        ;
      

這種解決方案也有一定的問(wèn)題。首先你必須能夠在服務(wù)器端部署代碼,某些小項(xiàng)目也許根本不需要服務(wù)器環(huán)境。

另一個(gè)可能更重要的原因是這種方式加倍了網(wǎng)絡(luò)流量。首先必須從外部域加載到你自己的域下,然后才被下載到你的SWF客戶端。同時(shí)這也加重了你的服務(wù)器的負(fù)載。使用跨域策略文件的話就不會(huì)有這種問(wèn)題。

這可以作為一種解決方案,但最好還是能用跨域策略文件來(lái)解決。

SWF Communication Without Trust 在非受信的SWF之間通訊

在某些情況下有可能要與其他來(lái)源不那么可靠的域中的SWF通訊,你并不希望完全信任該域,放開全部授權(quán)。對(duì)此LoaderInfo對(duì)象的sharedEvents屬性提供了另一種機(jī)制。sharedEvents對(duì)象是唯一的一個(gè)可以在不同安全域中發(fā)送共享事件的對(duì)象。加載者和被加載者都可以通過(guò)這個(gè)對(duì)象來(lái)向?qū)Ψ桨l(fā)送事件。

通過(guò)sharedEvents對(duì)象發(fā)送的事件在兩個(gè)域中都是完全受信的,這就使得在兩個(gè)安全域中傳遞的任意數(shù)據(jù)都無(wú)需考慮安全問(wèn)題。

警告 :當(dāng)心!通過(guò)sharedEvents對(duì)象傳遞了錯(cuò)誤的數(shù)據(jù)仍然有可能把你的SWF中的數(shù)據(jù)暴露出去。比如你的事件包含了一個(gè)復(fù)雜對(duì)象,特別是顯示列表上的對(duì)象,那么你的整個(gè)SWF都將暴露。

所以通過(guò)sharedEvents發(fā)送的事件應(yīng)該限制為包含簡(jiǎn)單數(shù)據(jù)的事件類型,避免一些被包含后門的SWF程序加以利用。如果你要傳遞復(fù)雜的事件,那要在傳遞之前先做一下清理。

使用sharedEvents進(jìn)行通訊的兩個(gè)SWF需要確保發(fā)送和接收的是一致的事件類型。父SWF可以發(fā)出一種事件并監(jiān)聽另一種。子SWF可以監(jiān)聽父SWF發(fā)出的事件并發(fā)出父SWF中正在監(jiān)聽的事件。這些事件的名字可以是隨意的。

下面的例子演示了在不同安全域中的父子SWF使用sharedEvents來(lái)通訊簡(jiǎn)單的文本信息的情況。父SWF發(fā)出“fromParent”事件,而子SWF發(fā)出“fromChild”事件。

http://safe.example.com/parent.swf:

        
          var
        
         loader:Loader = 
        
          new
        
         Loader
        
          (
        
        
          )
        
        ;

        
          var
        
         shared:EventDispatcher = loader.
        
          contentLoaderInfo
        
        .
        
          sharedEvents
        
        ;
shared.
        
          addEventListener
        
        
          (
        
        
          "fromChild"
        
        , fromChild
        
          )
        
        ;


        
          var
        
        
          url
        
        :
        
          String
        
         = 
        
          "http://untrusted.example.com/child.swf"
        
        ;
loader.
        
          load
        
        
          (
        
        
          new
        
         URLRequest
        
          (
        
        
          url
        
        
          )
        
        
          )
        
        ;


        
          function
        
         fromChild
        
          (
        
        event:TextEvent
        
          )
        
        :
        
          void
        
        
          {
        
        
          trace
        
        
          (
        
        event.
        
          text
        
        
          )
        
        ; 
        
          // Good day
        
        
          var
        
         replyMessage:TextEvent = 
        
          new
        
         TextEvent
        
          (
        
        
          "fromParent"
        
        
          )
        
        ;
	replyMessage.
        
          text
        
         = 
        
          "Same to you"
        
        ;
	shared.
        
          dispatchEvent
        
        
          (
        
        replyMessage
        
          )
        
        ;

        
          }
        
      

http://untrusted.example.com/child.swf:

        
          var
        
         shared:EventDispatcher = loaderInfo.
        
          sharedEvents
        
        ;
shared.
        
          addEventListener
        
        
          (
        
        
          "fromParent"
        
        , fromParent
        
          )
        
        ;


        
          var
        
         firstMessage:TextEvent = 
        
          new
        
         TextEvent
        
          (
        
        
          "fromChild"
        
        
          )
        
        ;
firstMessage.
        
          text
        
         = 
        
          "Good Day"
        
        ;
shared.
        
          dispatchEvent
        
        
          (
        
        firstMessage
        
          )
        
        ;


        
          function
        
         fromParent
        
          (
        
        event:TextEvent
        
          )
        
        :
        
          void
        
        
          {
        
        
          trace
        
        
          (
        
        event.
        
          text
        
        
          )
        
        ; 
        
          // Same to you
        
        
          }
        
      

任意的事件類都可以像這樣用于傳遞信息,也包括自定義事件。再次強(qiáng)調(diào),要當(dāng)心不要把包含引用的數(shù)據(jù)(特別是顯示列表上的對(duì)象)隨著事件一起發(fā)送出去。這種情況的例子在 場(chǎng)景的擁有者和獲取權(quán)限 章節(jié)中可以找到。

Merging Security Domains 合并安全域

如果兩個(gè)域之間建立了信任關(guān)系,一個(gè)SWF就能把另外一個(gè)SWF加到自己的安全域內(nèi),就像是在相同的域下一樣。

在這種情況下信任授權(quán)的處理有少許不同。首先,包含父SWF的域不需要指定什么,只要執(zhí)行加載另一個(gè)SWF到當(dāng)前的安全域就表示完全信任這個(gè)SWF。

其次,因?yàn)樽覵WF是立即被加載到父SWF的安全域中,并沒有機(jī)會(huì)通過(guò)allowDomain進(jìn)行信任授權(quán)聲明。當(dāng)子SWF可以執(zhí)行allowDomain聲明的時(shí)候,已經(jīng)被加載并實(shí)例化到另外的域中。所以這種情況下,跨域策略文件將派上用場(chǎng)。實(shí)際上這也是跨域策略文件唯一適用于對(duì)SWF進(jìn)行授權(quán)的情況。

Loading into another security domain

需要跨域策略文件把跨域的SWF加載到相同的安全域

要加載某個(gè)SWF到自己的安全域內(nèi),需要給Loader.load方法指定一個(gè) LoaderContext 對(duì)象。LoaderContext對(duì)象的securityDomain屬性設(shè)置為當(dāng)前的安全域( SecurityDomain.currentDomain )。通過(guò)這樣的加載方式,父SWF授信給子SWF,而子SWF的授信則需要通過(guò)跨域策略文件。

http://host.example.com/parent.swf:

        
          trace
        
        
          (
        
        
          new
        
        
          LocalConnection
        
        
          (
        
        
          )
        
        .
        
          domain
        
        
          )
        
        ; 
        
          // host.example.com
        
        
          var
        
         loader:Loader = 
        
          new
        
         Loader
        
          (
        
        
          )
        
        ;


        
          // 創(chuàng)建一個(gè)LoaderContext對(duì)象把子SWF加載到當(dāng)前的安全域
        
        
          var
        
         context:LoaderContext = 
        
          new
        
         LoaderContext
        
          (
        
        
          true
        
        
          )
        
        ;
context.
        
          securityDomain
        
         = SecurityDomain.
        
          currentDomain
        
        ;


        
          var
        
        
          url
        
        :
        
          String
        
         = 
        
          "http://trusting.example.com/child.swf"
        
        ;
loader.
        
          load
        
        
          (
        
        
          new
        
         URLRequest
        
          (
        
        
          url
        
        
          )
        
        , context
        
          )
        
        ;
      

http://trusting.example.com/crossdomain.xml:

        <?xml version="1.0"?>
<cross-domain-policy>
	<allow-access-from domain="host.example.com"/>
</cross-domain-policy>
      

http://trusting.example.com/child.swf:

        
          trace
        
        
          (
        
        
          new
        
        
          LocalConnection
        
        
          (
        
        
          )
        
        .
        
          domain
        
        
          )
        
        ; 
        
          // host.example.com
        
      

我們可以通過(guò) LocalConnection 對(duì)象的domain屬性來(lái)檢查每個(gè)SWF所處的安全域。雖然子SWF原先所處的域是trusting.example.com,但是由于它被加載到父SWF所處的域中,所以子SWF最終所處的安全域是host.example.com。

用這個(gè)方式加載的SWF文件權(quán)力比用allowDomain授權(quán)的更加大。使用allowDomain授權(quán),等同于 說(shuō)你能做什么,我就能做什么 。而把SWF加載到同一個(gè)安全域,則等同于 我能做任何事 。在前一種情況下,子SWF只能調(diào)用父SWF下的代碼,還是受限于父SWF中的定義。但是通過(guò)加載到相同的安全域,這些子SWF就可以在你的域下面做任意操作,這包括:

  • 獲取父SWF中的任意引用
  • 讀取主域中的所有文件
  • 讀取其他授信給主域的所有域下的文件
  • 讀取主域下的共享對(duì)象
  • 獲取通過(guò)主域建立的共享連接通訊
  • 獲取授信給主域的socket連接

所以在引入跨域SWF文件到你當(dāng)前的安全域下的時(shí)候,你要確保這種權(quán)力不會(huì)被濫用。

使用包含安全域的LoaderContext對(duì)象的load方法不是能夠引入跨域SWF到你的安全域的唯一方法。Loader類的另一個(gè)方法loadBytes也可以做到。和load不同的是,它不是用URL來(lái)加載外部?jī)?nèi)容,而是直接加載以 ByteArray 的形式加載對(duì)象。

由于ByteArray與域名之間沒有關(guān)聯(lián),所以用loadBytes方法加載的對(duì)象將直接進(jìn)入當(dāng)前安全域內(nèi)。因?yàn)槟阍诩虞d包含這些字節(jié)對(duì)象之前往往都要經(jīng)過(guò)某種信任授權(quán),所以這通常是安全的。

http://host.example.com/parent.swf:

        
          trace
        
        
          (
        
        
          new
        
        
          LocalConnection
        
        
          (
        
        
          )
        
        .
        
          domain
        
        
          )
        
        ; 
        
          // host.example.com
        
        
          var
        
         loader:Loader = 
        
          new
        
         Loader
        
          (
        
        
          )
        
        ;


        
          var
        
         urlLoader:URLLoader = 
        
          new
        
         URLLoader
        
          (
        
        
          )
        
        ;
urlLoader.
        
          dataFormat
        
         = URLLoaderDataFormat.
        
          BINARY
        
        ;
urlLoader.
        
          addEventListener
        
        
          (
        
        Event.
        
          COMPLETE
        
        , 
        
          bytesLoaded
        
        
          )
        
        ;


        
          // cross-domain policy file required to load data
        
        
          var
        
        
          url
        
        :
        
          String
        
         = 
        
          "http://trusting.example.com/childbytes.swf"
        
        ;
urlLoader.
        
          load
        
        
          (
        
        
          new
        
         URLRequest
        
          (
        
        
          url
        
        
          )
        
        
          )
        
        ;


        
          function
        
        
          bytesLoaded
        
        
          (
        
        event:Event
        
          )
        
        :
        
          void
        
        
          {
        
        
	loader.
        
          loadBytes
        
        
          (
        
        urlLoader.
        
          data
        
        
          )
        
        ;

        
          }
        
      

http://trusting.example.com/crossdomain.xml:

        <?xml version="1.0"?>
<cross-domain-policy>
	<allow-access-from domain="host.example.com"/>
</cross-domain-policy>
      

http://trusting.example.com/childbytes.swf:

        
          trace
        
        
          (
        
        
          new
        
        
          LocalConnection
        
        
          (
        
        
          )
        
        .
        
          domain
        
        
          )
        
        ; 
        
          // host.example.com
        
      

就和前面看到的例子一樣,通過(guò)檢查子SWF文件的LocalConnection.domain屬性,使用loadBytes方法加載的子SWF也顯示為相同的安全域。

警告 :loadBytes方法有個(gè)小小的安全問(wèn)題:可以把授信過(guò)的跨域SWF和加載到當(dāng)前安全域下的SWF兩者間的不同扯平。我們知道雖然這兩者都是被信任的,但是就像上面的列表中提到的,后者比前者的權(quán)力更大?!? 你能做什么,我就能做什么 ”與“ 我能做任何事 ”之間的差別,結(jié)果可以變成沒有差別。

這是因?yàn)槭谛胚^(guò)的跨域SWF文件可以訪問(wèn)父SWF的任何對(duì)象,包括父SWF對(duì)象的Loader實(shí)例,一旦擁有了對(duì)loadBytes方法的引用,這就意味著可以把某些字節(jié)對(duì)象加載到當(dāng)前的安全域。

下面的這個(gè)例子展示了這種可能性:

http://good.example.com/parent.swf:

        
          // 授權(quán) "你能做什么,我就能做什么"
        
        
Security.
        
          allowDomain
        
        
          (
        
        
          "evil.example.com"
        
        
          )
        
        ;


        
          // 應(yīng)當(dāng)受保護(hù)的數(shù)據(jù)
        
        
          var
        
         so:
        
          SharedObject
        
         = 
        
          SharedObject
        
        .
        
          getLocal
        
        
          (
        
        
          "foo"
        
        , 
        
          "/"
        
        
          )
        
        ;
so.
        
          data
        
        .
        
          foo
        
         = 
        
          "bar"
        
        ;
so.
        
          flush
        
        
          (
        
        
          )
        
        ;


        
          var
        
         loader:Loader = 
        
          new
        
         Loader
        
          (
        
        
          )
        
        ;

        
          var
        
        
          url
        
        :
        
          String
        
         = 
        
          "http://evil.example.com/child.swf"
        
        ;
loader.
        
          load
        
        
          (
        
        
          new
        
         URLRequest
        
          (
        
        
          url
        
        
          )
        
        
          )
        
        ;
      

http://evil.example.com/child.swf:

        
          var
        
         so:
        
          SharedObject
        
         = 
        
          SharedObject
        
        .
        
          getLocal
        
        
          (
        
        
          "foo"
        
        , 
        
          "/"
        
        
          )
        
        ;

        
          trace
        
        
          (
        
        
          "trust only: "
        
         + so.
        
          data
        
        .
        
          foo
        
        
          )
        
        ; 
        
          // trust only: undefined
        
        
          var
        
         urlLoader:URLLoader = 
        
          new
        
         URLLoader
        
          (
        
        
          )
        
        ;
urlLoader.
        
          dataFormat
        
         = URLLoaderDataFormat.
        
          BINARY
        
        ;
urlLoader.
        
          addEventListener
        
        
          (
        
        Event.
        
          COMPLETE
        
        , 
        
          bytesLoaded
        
        
          )
        
        ;


        
          var
        
        
          url
        
        :
        
          String
        
         = 
        
          "http://evil.example.com/childbytes.swf"
        
        ;
urlLoader.
        
          load
        
        
          (
        
        
          new
        
         URLRequest
        
          (
        
        
          url
        
        
          )
        
        
          )
        
        ;


        
          function
        
         bytesLoadedEvent
        
          )
        
        :
        
          void
        
        
          {
        
        
          // 威脅!loadBytes加載了SWF數(shù)據(jù)到父SWF的安全域
        
        
	loaderInfo.
        
          loader
        
        .
        
          loadBytes
        
        
          (
        
        urlLoader.
        
          data
        
        
          )
        
        ;

        
          }
        
      

http://evil.example.com/childbytes.swf:

        
          var
        
         so:
        
          SharedObject
        
         = 
        
          SharedObject
        
        .
        
          getLocal
        
        
          (
        
        
          "foo"
        
        , 
        
          "/"
        
        
          )
        
        ;

        
          trace
        
        
          (
        
        
          "same domain: "
        
         + so.
        
          data
        
        .
        
          foo
        
        
          )
        
        ; 
        
          // same domain: ba
        
      

將來(lái)版本的Flash Player可能會(huì)改變這種行為,所以在程序中不要使用這種方法。我們應(yīng)該關(guān)注的是加載授信過(guò)的SWF文件會(huì)帶來(lái)的潛在威脅:暴露你的域下的所有數(shù)據(jù)。

Stage Owner and Access 場(chǎng)景的擁有者和獲取權(quán)限

當(dāng)?shù)谝粋€(gè)SWF文件被加載到Flash Player中的時(shí)候,它被加到顯示列表的根上,也就是我們所說(shuō)的 stage 對(duì)象。這也是Flash Player自己的顯示對(duì)象的根。每個(gè)SWF都有代表自己主文檔類或者主時(shí)間線的根(叫做 root )。第一個(gè)被創(chuàng)建的SWF實(shí)例的根被放置于場(chǎng)景上,其他子SWF使用Loader對(duì)象的實(shí)例來(lái)加載。

場(chǎng)景的特別之處在于它本身就位于顯示列表上,所有處于顯示列表上的子SWF都可以取得它的引用,但是它只有一個(gè)擁有者:就是第一個(gè)被實(shí)例化的那個(gè)SWF。場(chǎng)景的擁有者決定了場(chǎng)景所連接的安全域。其他的SWF想對(duì)場(chǎng)景進(jìn)行特殊操作的行為都必須獲得場(chǎng)景所有者的信任授權(quán)。

你可能有注意到在過(guò)去的有些程序或者是組件中,被加載到不同的域(未授信)里的時(shí)候報(bào)錯(cuò)。這正是因?yàn)闆]有取得對(duì)場(chǎng)景對(duì)象進(jìn)行操作的授權(quán)。因?yàn)閳?chǎng)景對(duì)象是可以被引用的,但是諸如場(chǎng)景的addEventListener方法等卻不可用,所以這很容易引起誤解。

下面這個(gè)表格列出了場(chǎng)景對(duì)象限制非安全域?qū)ο笤L問(wèn)的成員??赡懿皇?00%精確,主要用于參考。

addChild addChildAt removeChild
removeChildAt getChildIndex setChildIndex
getChildAt getObjectsUnderPoint swapChildren
swapChildrenAt numChildren tabChildren
mouseChildren width stageWidth
fullScreenWidth height stageHeight
fullScreenHeight quality align
scaleMode displayState fullScreenSourceRect
stageFocusRect showDefaultContextMenu colorCorrection
addEventListener dispatchEvent hasEventListener
willTrigger

在下面的例子中看看場(chǎng)景是如何可以被子SWF訪問(wèn),但是卻不能調(diào)用stage.addEventListener方法。

http://first.example.com/parent.swf:

        
          var
        
         loader:Loader = 
        
          new
        
         Loader
        
          (
        
        
          )
        
        ;
addChild
        
          (
        
        loader
        
          )
        
        ;


        
          var
        
        
          url
        
        :
        
          String
        
         = 
        
          "http://<samp>second</samp>.example.com/child.swf"
        
        ;
loader.
        
          load
        
        
          (
        
        
          new
        
         URLRequest
        
          (
        
        
          url
        
        
          )
        
        
          )
        
        ;
      

http://second.example.com/child.swf:

        
          // Works
        
        
          trace
        
        
          (
        
        
          stage
        
        
          )
        
        ; 
        
          // [object Stage]
        
        
          // Does not work
        
        
          stage
        
        .
        
          addEventListener
        
        
          (
        
        MouseEvent.
        
          CLICK
        
        , stageClick
        
          )
        
        ;

        
          // SecurityError: Error #2070: Security sandbox violation:
        
        
          // caller http://second.example.com/child.swf cannot access
        
        
          // Stage owned by http://first.example.com/parent.swf.
        
      

場(chǎng)景的這種所有者關(guān)系非常操蛋,因?yàn)槲覀兘?jīng)常需要對(duì)場(chǎng)景對(duì)象監(jiān)聽鼠標(biāo)或者鍵盤事件,比如檢測(cè)鍵盤按下或者檢測(cè)鼠標(biāo)在物體外部釋放點(diǎn)擊。在這種情況下,單靠子SWF自身是沒辦法完成的。還好,場(chǎng)景擁有者的父SWF可以通過(guò)sharedEvents傳遞場(chǎng)景事件而不必授信給子SWF。通過(guò)這種方式,可以在保護(hù)主域的前提下配合完成這種工作。

警告 :以下這個(gè)使用范例演示了sharedEvents是如何處理安全性問(wèn)題的。一些鼠標(biāo)事件的relatedObject屬性持有對(duì)時(shí)間線上的對(duì)象的引用。如果不經(jīng)過(guò)清理,這些對(duì)象就會(huì)暴露給沒有經(jīng)過(guò)授信的域。所以通過(guò)sharedEvents發(fā)送事件時(shí),要把這些引用清除。比如MouseEvent,我們可以新建一個(gè)僅包含必須數(shù)據(jù)的MouseEvent對(duì)象。

下面的示例展示了如何通過(guò)sahredEvents發(fā)送場(chǎng)景事件。示例中僅僅轉(zhuǎn)發(fā)了MOUSE_OUT事件,當(dāng)然也可以擴(kuò)展于其他的事件類型。注意如何創(chuàng)建一個(gè)代理事件并保護(hù)父SWF中的對(duì)象。

http://stageowner.example.com/parent.swf:

        
          var
        
         combination:
        
          String
        
         = 
        
          "1-2-3-4-5"
        
        ; 
        
          // 隱私數(shù)據(jù)
        
        
          var
        
         loader:Loader = 
        
          new
        
         Loader
        
          (
        
        
          )
        
        ;

        
          var
        
         shared:EventDispatcher = loader.
        
          contentLoaderInfo
        
        .
        
          sharedEvents
        
        ;


        
          var
        
        
          url
        
        :
        
          String
        
         = 
        
          "http://untrusted.example.com/child.swf"
        
        ;
loader.
        
          load
        
        
          (
        
        
          new
        
         URLRequest
        
          (
        
        
          url
        
        
          )
        
        
          )
        
        ;


        
          stage
        
        .
        
          addEventListener
        
        
          (
        
        MouseEvent.
        
          MOUSE_OUT
        
        , forwardMouseEvent
        
          )
        
        ;


        
          function
        
         forwardMouseEvent
        
          (
        
        event:MouseEvent
        
          )
        
        :
        
          void
        
        
          {
        
        
          // 威脅!這種做法暴露了relatedObject,也使得其他數(shù)據(jù)被暴露
        
        
          //shared.dispatchEvent(event);
        
        
          // Safer: 創(chuàng)建一個(gè)清理過(guò)的代理事件來(lái)切斷relatedObject的引用
        
        
          var
        
         safeEvent:MouseEvent = 
        
          new
        
         MouseEvent
        
          (
        
        event.
        
          type
        
        
          )
        
        ;
	safeEvent.
        
          altKey
        
         = event.
        
          altKey
        
        ;
	safeEvent.
        
          buttonDown
        
         = event.
        
          buttonDown
        
        ;
	safeEvent.
        
          ctrlKey
        
         = event.
        
          ctrlKey
        
        ;
	safeEvent.
        
          delta
        
         = event.
        
          delta
        
        ;
	safeEvent.
        
          localX
        
         = event.
        
          localX
        
        ;
	safeEvent.
        
          localY
        
         = event.
        
          localY
        
        ;
	safeEvent.
        
          shiftKey
        
         = event.
        
          shiftKey
        
        ;

	shared.
        
          dispatchEvent
        
        
          (
        
        safeEvent
        
          )
        
        ;

        
          }
        
      

http://untrusted.example.com/child.swf:

        
          var
        
         shared:EventDispatcher;


        
          // 如果場(chǎng)景事件不能引用,那就通過(guò)sharedEvents監(jiān)聽
        
        
          if
        
        
          (
        
        loaderInfo.
        
          parentAllowsChild
        
        
          )
        
        
          {
        
        
          stage
        
        .
        
          addEventListener
        
        
          (
        
        MouseEvent.
        
          MOUSE_OUT
        
        , stageMouseOut
        
          )
        
        ;

        
          }
        
        
          else
        
        
          {
        
        
	shared = loaderInfo.
        
          sharedEvents
        
        ;
	shared.
        
          addEventListener
        
        
          (
        
        MouseEvent.
        
          MOUSE_OUT
        
        , stageMouseOut
        
          )
        
        ;

        
          }
        
        
          function
        
         stageMouseOut
        
          (
        
        event:MouseEvent
        
          )
        
        :
        
          void
        
        
          {
        
        
          // -- stage mouse out actions here --
        
        
          // 如果sharedEvents傳遞了原始的鼠標(biāo)事件,那么父域中的數(shù)據(jù)就暴露了!
        
        
          //trace(Object(event.relatedObject).root.combination); // 1-2-3-4-5
        
        
          }
        
      

幸好有safeEvent這個(gè)MouseEvent的實(shí)例,原本的MouseEvent對(duì)象的relatedObject指向的引用被屏蔽了。實(shí)際上,所有通過(guò)sharedEvents對(duì)象發(fā)送的事件都應(yīng)該用這種方式清理一遍。

Local Security Domains 本地安全域

在硬盤上運(yùn)行的SWF文件同樣有自己的安全域。本地安全域有自己獨(dú)特的行為,共分為4種安全沙箱類型:local-with-file, local-with-network, local-trusted, and application for AIR(本文不詳細(xì)討論AIR)。再加上網(wǎng)絡(luò)上的SWF,一共有5種安全沙箱。在ActionScript中,你可以用 Security.sandboxType 來(lái)獲得當(dāng)前的安全沙箱類型。

  • local-with-file ( Security.LOCAL_WITH_FILE )—本地不受信任的文件,只可以訪問(wèn)本地?cái)?shù)據(jù),不能與網(wǎng)絡(luò)通信。
  • local-with-network ( Security.LOCAL_WITH_NETWORK )—本地不受信任的文件,只可以訪問(wèn)網(wǎng)絡(luò),但是不能讀取本地?cái)?shù)據(jù)。
  • local-trusted ( Security.LOCAL_TRUSTED )—本地受信的文件,通過(guò)Flash Player設(shè)置管理器或者FlashPlayerTrust文件授權(quán)??梢栽L問(wèn)本地和網(wǎng)絡(luò)。
  • application ( Security.APPLICATION )—隨著AIR包而安裝,運(yùn)行在AIR程序中。默認(rèn)在這種沙箱類型下的文件可以調(diào)用任意域下的文件(外部域可能不允許)。而且默認(rèn)能從任意其他域下加載數(shù)據(jù)。
  • remote ( Security.REMOTE )—來(lái)自網(wǎng)絡(luò)的文件,遵循安全域的沙箱規(guī)則。

由于有可能從用戶的硬盤上獲取敏感數(shù)據(jù),所以本地文件在安全方面有著嚴(yán)格的規(guī)則。一旦有機(jī)會(huì),惡意的SWF將可以從電腦上讀取數(shù)據(jù)并上傳到網(wǎng)絡(luò)上的服務(wù)器。所以為了防止這種情況,本地的SWF只允許一種類型的通訊,要么就是本地,要么就是網(wǎng)絡(luò)。而且,不同安全沙箱類型的SWF不能相互加載,避免能同時(shí)訪問(wèn)網(wǎng)絡(luò)和訪問(wèn)本地的情況出現(xiàn)。

由于我們不能判斷本地文件的域名,所以判斷本地SWF文件的安全沙箱用的是另外一種形式。只允許本地和只允許網(wǎng)絡(luò)這兩種情況是通過(guò)SWF文件內(nèi)的標(biāo)識(shí)來(lái)區(qū)分的,所有的SWF在發(fā)布的時(shí)候都帶有這種標(biāo)識(shí),當(dāng)SWF在本地運(yùn)行的時(shí)候,F(xiàn)lash Player就用它來(lái)檢測(cè)安全沙箱類型。

對(duì)于本地的信任文件,相同的問(wèn)題是我們沒有地方來(lái)保存跨域策略文件,所以我們通過(guò)Flash Player的 設(shè)置管理器 里的 全局安全設(shè)置面板 來(lái)設(shè)置。通過(guò)下圖中所示的下拉菜單把本地SWF的路徑添加到本地的安全文件列表里。

Settings Manager

Flash Player 設(shè)置管理器

另一種方式是通過(guò)配置文件的方式。配置文件不像設(shè)置管理器那樣需要聯(lián)網(wǎng)來(lái)使用。要把SWF或者包含SWF的文件夾添加到信任位置的話只需要添加路徑到Flash Player的#Security\FlashPlayerTrust下的.cfg文件就可以了。在Mac和Windows上,這個(gè)路徑如下:

  • Windows 95-XP:
    C:\Documents and Settings\ [username] \Application Data\Macromedia\Flash Player\#Security\FlashPlayerTrust
  • Windows Vista-7:
    C:\Users\ [username] \AppData\Roaming\Macromedia\Flash Player\#Security\FlashPlayerTrust
  • Mac OS X:
    /Users/ [username] /Library/Preferences/Macromedia/Flash Player/#Security/FlashPlayerTrust

[username] 替換為你的用戶名。

兩種方法都是把信任授權(quán)信息寫入你的硬盤(全局安全設(shè)置面板也一樣,保存在Flash Player的特定目錄下)。這些文件就像你本地的跨域策略文件一樣。當(dāng)Flash Player讀取的時(shí)候,信任授權(quán)給SWF,并覆蓋SWF文件中關(guān)于本地訪問(wèn)權(quán)限的標(biāo)識(shí),從而允許受信的SWF能夠同時(shí)訪問(wèn)本地和網(wǎng)絡(luò)。

Local sandbox types
本地安全域

關(guān)于本地信任機(jī)制還有一點(diǎn)需要注意的是即使是本地受信的文件,仍然不能把處于外部沙箱的內(nèi)容加載入本地沙箱。

大多數(shù)Flash內(nèi)容都是為網(wǎng)絡(luò)創(chuàng)建的,所以通常不需要完全理解本地的安全沙箱機(jī)制。但是開發(fā)和測(cè)試是一個(gè)例外。Flash編輯器在測(cè)試的時(shí)候就是把SWF放在一個(gè)本地受信的安全沙箱里面。這有可能會(huì)造成與真正發(fā)布的SWF情況不同的結(jié)果,因?yàn)閮烧叩陌踩诚洳煌?。比如你測(cè)試的時(shí)候可以從沒有授信的外部域讀取內(nèi)容,而真正發(fā)布到網(wǎng)站上的SWF卻無(wú)法加載。所以當(dāng)你測(cè)試的時(shí)候要注意,你所看到的結(jié)果和最終發(fā)布的版本有可能不一樣。

你可以到 Flash Player Developer Center (adobe.com)的 Security section 查看更詳細(xì)的安全相關(guān)信息。

第一部分到此結(jié)束,第二部分Application Domain請(qǐng) 點(diǎn)擊 。

深入理解Flash的沙箱 – Security Domains-1


更多文章、技術(shù)交流、商務(wù)合作、聯(lián)系博主

微信掃碼或搜索:z360901061

微信掃一掃加我為好友

QQ號(hào)聯(lián)系: 360901061

您的支持是博主寫作最大的動(dòng)力,如果您喜歡我的文章,感覺我的文章對(duì)您有幫助,請(qǐng)用微信掃描下面二維碼支持博主2元、5元、10元、20元等您想捐的金額吧,狠狠點(diǎn)擊下面給點(diǎn)支持吧,站長(zhǎng)非常感激您!手機(jī)微信長(zhǎng)按不能支付解決辦法:請(qǐng)將微信支付二維碼保存到相冊(cè),切換到微信,然后點(diǎn)擊微信右上角掃一掃功能,選擇支付二維碼完成支付。

【本文對(duì)您有幫助就好】

您的支持是博主寫作最大的動(dòng)力,如果您喜歡我的文章,感覺我的文章對(duì)您有幫助,請(qǐng)用微信掃描上面二維碼支持博主2元、5元、10元、自定義金額等您想捐的金額吧,站長(zhǎng)會(huì)非常 感謝您的哦?。。?/p>

發(fā)表我的評(píng)論
最新評(píng)論 總共0條評(píng)論