<output id="qn6qe"></output>

    1. <output id="qn6qe"><tt id="qn6qe"></tt></output>
    2. <strike id="qn6qe"></strike>

      亚洲 日本 欧洲 欧美 视频,日韩中文字幕有码av,一本一道av中文字幕无码,国产线播放免费人成视频播放,人妻少妇偷人无码视频,日夜啪啪一区二区三区,国产尤物精品自在拍视频首页,久热这里只有精品12

      可信前端之路-代碼保護

      可信前端之路-代碼保護

      莫念@阿里安全

      0x00 前言

      在信息安全領域,可信系統(Trusted system)是一個讓人心動的目標,它指的是一個通過實施特定的安全策略而達到一定可信程度的系統。

      在計算機中,可信平臺模塊(Trusted Platform Module,TPM)已經投入使用,它符合可信賴計算組織(Trusted Computing Group,TCG)制定的TPM規范,是為了實現可信系統目標的而打造的一款安全芯片。作為可信系統的信任根,TPM是可信計算的核心模塊,為計算機安全提供了強有力的保障。

      而在我們的web系統中,想打造一個可信系統似乎是個偽命題,“永遠不要相信客戶端的輸入”是基本的安全準則。實際上,在可信系統中的可信也并不是說真的是絕對安全,維基上對其的解釋為:“可信的”(Trusted)未必意味著對用戶而言是“值得信賴的”(Trustworthy)。確切而言,它意味著可以充分相信其行為會更全面地遵循設計,而執行設計者和軟件編寫者所禁止的行為的概率很低。

      從這個角度講,我們把其當做一個美好的愿景,我們希望能夠構造一個web系統中的TPM,可以把惡意行為控制在一定的概率之內,從而實現一個相對可信的web系統。

      0x01 可信前端

      在可信系統中,TPM的一個重要作用就是鑒別消息來源的真實性,保障終端的可信。在web系統中,我們的消息來源就是用戶。隨著撞庫、惡意注冊、薅羊毛等產業的蓬勃發展,在越來越多的場景我們需要鑒別請求數據是否來自真實的用戶,保護真實用戶的數據安全。

      所以想要構造一個web系統中的TPM,首要問題就是需要保證輸入數據安全,打造一個相對可信的前端環境。但是由于web的開放特性,前端作為數據采集的最前線,js代碼始終暴露在外,在這種情況下,防止惡意偽造請求變得非常困難,可信前端也就成了無稽之談。

      在反復對抗中,代碼保護也就是通常意義上的js代碼混淆的重要性逐漸彰顯出來。今天我就想和大家聊一聊js混淆的問題。

      1、為什么需要js混淆

      顯而易見,是為了保護我們的前端代碼邏輯。

      在web系統發展早期,js在web系統中承擔的職責并不多,只是簡單的提交表單,js文件非常簡單,也不需要任何的保護。

      隨著js文件體積的增大,為了縮小js體積,加快http傳輸速度,開始出現了很多對js的壓縮工具,比如 uglify、compressor、clouser。。。它們的工作主要是

          · 合并多個js文件

          · 去除js代碼里面的空格和換行

          · 壓縮js里面的變量名

          · 剔除掉注釋

      【壓縮后的代碼】

      雖然壓縮工具出發點都是為了減少js文件的體積,但是人們發現壓縮替換后的代碼已經比源代碼可讀性差了很多,間接起到了代碼保護的作用,于是壓縮js文件成為了前端發布的標配之一。但是后來市面上主流瀏覽器chrome、Firefox等都提供了js格式化的功能,能夠很快的把壓縮后的js美化,再加上現代瀏覽器強大的debug功能,單純壓縮過的js代碼對于真正懷有惡意的人,已經不能起到很好的防御工作,出現了"防君子不防小人"的尷尬局面。

      【chrome開發者工具格式化之后的代碼】

      而在web應用越來越豐富的今天,伴隨著瀏覽器性能和網速的提高,js承載了更多的工作,不少后端邏輯都在向前端轉移,與此同時也讓更多的不法分子有機可乘。在web模型中,js往往是不法分子的第一個突破口。知曉了前端邏輯,不法分子可以模擬成一個正常的用戶來實施自己的惡意行為。所以,在很多登錄、注冊、支付、交易等等頁面中,關鍵業務和風控系統依賴的js都不希望被人輕易的破解,js混淆應運而生。

      2、js混淆是不是紙老虎

      這是一個老生常談的問題。實際上,代碼混淆早就不是一個新鮮的名詞,在桌面軟件時代,大多數的軟件都會進行代碼混淆、加殼等手段來保護自己的代碼。Java和.NET都有對應的混淆器。黑客們對這個當然也不陌生,許多病毒程序為了反查殺,也會進行高度的混淆。只不過由于js是動態腳本語言,在http中傳輸的就是源代碼,逆向起來要比打包編譯后的軟件簡單很多,很多人因此覺得混淆是多此一舉。

      【.NET混淆器dotFuscator】

      其實正是因為js傳輸的就是源代碼,我們才需要進行混淆,暴露在外的代碼沒有絕對的安全,但是在對抗中,精心設計的混淆代碼能夠給破壞者帶來不小的麻煩,也能夠為防守者爭取更多的時間,相對于破解來說,混淆器規則的更替成本要小得多,在高強度的攻防中,可以大大增加破解者的工作量,起到防御作用。從這個角度來講,關鍵代碼進行混淆是必不可少的步驟。

      3、如何進行js混淆

      js混淆器大致有兩種:

      · 通過正則替換實現的混淆器

      · 通過語法樹替換實現的混淆器

      第一種實現成本低,但是效果也一般,適合對混淆要求不高的場景。第二種實現成本較高,但是更靈活,而且更安全,更適合對抗場景,我這里主要講一下第二種。基于語法層面的混淆器其實類似于編譯器,基本原理和編譯器類似,我們先對編譯器做一些基本的介紹。

      名詞解釋

      token: 詞法單元,也有叫詞法記號的,詞法分析器的產物,文本流被分割后的最小單位。

      AST: 抽象語法樹,語法分析器的產物,是源代碼的抽象語法結構的樹狀表現形式。

      【編譯器VS混淆器】

      編譯器工作流程

      簡單的說,當我們讀入一段字符串文本(source code),詞法分析器會把它拆成一個一個小的單位(token),比如數字1 是一個token, 字符串'abc'是一個token等等。接下來語法分析器會把這些單位組成一顆樹狀結構(AST),這個樹狀結構就代表了token們的組成關系。比如 1 + 2 就會展示成一棵加法樹,左右子節點分別是token - 1 和token - 2 ,中間token表示加法。編譯器根據生成的AST轉換到中間代碼,最終轉換成機器代碼。

      對編譯器更多細節感興趣的同學可以移步龍書:編譯原理

      混淆器工作流程

      編譯器需要把源代碼編譯成中間代碼或者機器碼,而我們的混淆器輸出其實還是js。所以我們從語法分析之后往下的步驟并不需要。想想我們的目標是什么,是修改原有的js代碼結構,在這里面這個結構對應的是什么呢?就是AST。任何一段正確的js代碼一定可以組成一顆AST,同樣,因為AST表示了各個token的邏輯關系,我們也可以通過AST反過來生成一段js代碼。所以,你只需要構造出一顆AST,就能生成任何js代碼!混淆過程如上右圖所示。

      通過修改AST生成一個新的AST,新的AST就可以對應新的JavaScript代碼。

      規則設計

      知道了大致的混淆流程,最重要的環節就是設計規則。我們上面說了,我們需要生成新的AST結構意味著會生成和源代碼不一樣的js代碼,但是我們的混淆是不能破壞原有代碼的執行結果的,所以混淆規則必須保證是在不破壞代碼執行結果的情況下,讓代碼變得更難以閱讀。

      具體的混淆規則各位可以自行根據需求設計,比如拆分字符串、拆分數組,增加廢代碼等等。

      參考:提供商業混淆服務的jscramble的混淆規則

      實現

      很多人看到這里就望而卻步,因為詞法分析和文法分析對編譯原理要求較高。其實這些現在都有工具可以幫助搞定了,借助工具,我們可以直接進行最后一步,對AST的修改。

      市面上JavaScript詞法和文法分析器有很多,比如其實v8就是一個,還有mozilla的SpiderMonkey, 知名的esprima等等,我這里要推薦的是uglify,一個基于nodejs的解析器。它具有以下功能:

          · parser,把 JavaScript 代碼解析成抽象語法樹

          · code generator,通過抽象語法樹生成代碼

          · scope analyzer,分析變量定義的工具

          · tree walker,遍歷樹節點

          · tree transformer,改變樹節點

      對比下我上面給出的混淆器設計的圖,發現其實只需要修改語法樹 這一步自己完成。

      實例

      說了這么多,可能很多人還是一頭霧水,為了幫助各位理解,我準備了一個簡單的例子,假設我們的混淆規則是想把 var a = 1; 中的數字1換成16進制,我們該如何設計混淆器呢。首先對源代碼做詞法分析和語法分析,uglify一個方法就搞定了,生成一顆語法樹,我們需要做的就是找到語法樹中的數字然后修改成16進制的結果,如下圖所示:

      實例代碼:

      var UglifyJS = require("uglify-js");
      
      var code = "var a = 1;";
      
      var toplevel = UglifyJS.parse(code); //toplevel就是語法樹
      
      var transformer = new UglifyJS.TreeTransformer(function (node) {
      
      if (node instanceof UglifyJS.AST_Number) { //查找需要修改的葉子節點
      
              node.value = '0x' + Number(node.value).toString(16);
      
              return node; //返回一個新的葉子節點 替換原來的葉子節點
      
          };
      
      });
      
      toplevel.transform(transformer);  //遍歷AST樹
      
      var ncode = toplevel.print_to_string(); //從AST還原成字符串
      
      console.log(ncode); // var a = 0x1;

      上面的代碼很簡單,首先通過parse方法構建語法樹,然后通過TreeTransformer遍歷語法樹,當遇到節點屬于UglifyJS.AST_Number類型(所有的AST類型見ast),這個token具有一個屬性 value 保存著數字類型的具體值,我們將其改成16進制表示,然后 return node 就會用新的節點代替原來的節點。

      效果展示

      貼一個我自己設計的混淆器混淆前后代碼:

       

      4、混淆對性能的影響

      由于增加了廢代碼,改變了原有的AST,混淆對性能肯定會造成一定的影響,但是我們可以通過規則來控制影響的大小。

          · 減少循環混淆,循環太多會直接影響代碼執行效率

          · 避免過多的字符串拼接,因為字符串拼接在低版本IE下面會有性能問題

          · 控制代碼體積,在插入廢代碼時應該控制插入比例,文件過大會給網絡請求和代碼執行都帶來壓力

      我們通過一定的規則完全可以把性能影響控制在一個合理的范圍內,實際上,有一些混淆規則反而會加快代碼的執行,比如變量名和屬性名的壓縮混淆,會減小文件體積,比如對全局變量的復制,會減少作用域的查找等等。在現代瀏覽器中,混淆對代碼的影響越來越小,我們只需要注意合理的混淆規則,完全可以放心的使用混淆。

      5、混淆的安全性

      混淆的目的是保護代碼,但是如果因為混淆影響了正常功能就舍本逐末了。

      由于混淆后的AST已經和原AST完全不同了,但是混淆后文件的和原文件執行結果必須一樣,如何保證既兼顧了混淆強度,又不破壞代碼執行呢?高覆蓋的測試必不可少:

          · 對自己的混淆器寫詳盡的單元測試

          · 對混淆的目標代碼做高覆蓋的功能測試,保證混淆前后代碼執行結果完全一樣

          · 多樣本測試,可以混淆單元測試已經完備了的類庫,比如混淆 Jquery 、AngularJS 等,然后拿混淆后的代碼去跑它們的單元測試,保證和混淆前執行結果完全一樣

      0x02 總結

          · 可信web系統是我們的愿景

          · 可信web系統離不開可信的前端環境

          · js混淆在對抗中必不可少

          · 實現一款自己的混淆器并沒有那么難

          · 混淆器對性能的影響是可控的

      0x03 參考

      https://en.wikipedia.org/wiki/Trusted_Platform_Module

      https://en.wikipedia.org/wiki/Trusted_system

      http://lisperator.net/uglifyjs

      http://esprima.org

       

       

      作者:莫念@阿里安全,更多安全類文章,請訪問阿里聚安全博客

      posted on 2016-09-08 14:25  阿里安全  閱讀(12106)  評論(23)    收藏  舉報

      主站蜘蛛池模板: 黑森林福利视频导航| 性欧美VIDEOFREE高清大喷水 | 中文字幕亚洲人妻系列| 欧洲美熟女乱av在免费| 欧美人妻在线一区二区| 国产成人一区二区不卡| 亚洲国产无套无码av电影| 日韩不卡无码精品一区高清视频| 97久久超碰精品视觉盛宴| 国产精品久久久久久免费软件| 国产精品熟女一区二区三区| 亚洲性线免费观看视频成熟| 邯郸县| 久久精品熟女亚洲av艳妇| 国产精品三级一区二区三区| 免费无遮挡无码永久视频| 欧洲码亚洲码的区别入口| 日韩一区国产二区欧美三区| 成人国产精品三上悠亚久久| 国内不卡一区二区三区| 精品一卡2卡三卡4卡乱码精品视频| 色爱综合激情五月激情| 99欧美日本一区二区留学生| 亚洲国产精品第一二三区| 亚洲一区二区约美女探花| 蜜桃av亚洲精品一区二区| 国产精品一区二区 尿失禁| 福利在线视频一区二区| 一区二区三区鲁丝不卡| 免费大片黄国产在线观看| 亚洲国产女性内射第一区| 亚洲精品乱码久久久久久蜜桃不卡| 九九热精品在线视频免费| 亚洲国产精品无码av| 亚洲免费一区二区av| 国产欧美综合在线观看第十页| 国产精品一区在线蜜臀 | 国产不卡精品视频男人的天堂| 国产精品午夜福利免费看| 欧美国产精品不卡在线观看| 欧美视频精品免费覌看|