天天看點

.NET源碼加密保護

我把Dotnet的保護分為三大類

  1. 由m$ 提供的非第三方保護方案

a)         強名稱 強名稱是MS提供的保護機制。 它需要使用 sn 這個指令。 強名稱是什麼意思呢?在這裡稍作解釋。強名稱的作用就是防止程式集被非法修改,當對程式集修改後,必須重新用您的私鑰再對程式集加一次強名稱,這也是如果含有強名稱的程式集在混淆或加密後必須要重新加強名稱的原因。 Sn / ? 可以看到它的使用方法,如果你安裝的 Framework是中文的,那麼參數的解釋也是中文的,我就不多講了。 那麼強名稱有用嗎?網上輕松破解強名稱的方法很多,Ildasm反編譯加過強名稱的程式集後,在IL檔案中将強名稱的相關資訊去掉,再利用Ilasm編譯,就可以解除強名稱的限制了。這個我已經過測試過,您的強名稱的PublcKey不管是加在程式集中,還是加在Class中,都可以被去掉,是以強名稱不是一個完善的保護方式。不過在這裡要說一下,如果有一個好的方案能和強名稱一起使用,那麼将建立一個非常好的機制,防修改,防濫用。 說到濫用,這是強名稱的一個特殊用途,它可以使您的dll不被第三方調用,如果您的dll能保護自己的話。 關于強命稱講到這裡,他的使用方式有必要的情況下,我們以後再深入的講解。   b)        編譯MSIL為本機代碼 (誤區?) 關于這一點,我經常能在MS上的社群看到有MVP這樣面對問題: 問:C#寫的程式能編譯成本機代碼嗎? 答:可以,使用 Ngen.exe 即可以 MSIL 代碼編譯為 本機代碼。 MVP這樣回答錯了嗎?其實,嚴格的說,MVP的回答是沒錯的,Ngen.exe的确是可以将 MSIL 編譯為本機代碼,并可以使JIT不需要進行再次編譯MSIL。這樣能加快程式的執行效率。 但使用者這樣的問題其實,并不是對執行效率不滿意,而是對中間語言不滿意,可惜 Ngen 并不能解決使用者的問題。 讓我們來淺淺的分析一下 Ngen的工作吧。 Ngen是MS提供的 本機映象生成器,它可以将中間語言程式集編譯為本機代碼存放在緩存中。這裡請大家注意,是存放在緩存中,Dotnet在記憶體中建立了一個緩存,這個緩存中存放了許多常用的程式集編譯後的本機代碼,它們是常駐的,由此來加快Dotnet的執行速度。 所謂一個本機代碼,因為本機映射時,會映射出一些 Framework 裡需要的Method,編譯為彙編就是 Call 0x0200000這樣的樣子,而這些東西必須是事件編譯好的。那麼理論上說 Ngen 必須要在目前執行的機器上運作,而直接編譯成本機代碼的程式copy到另一個地方不一定可以用,而且我一直沒有找到能将緩存中的本機代碼 copy 出來的方法。 講到這裡,不知道大家明白我的意思沒有,不管如何 Ngen.exe 隻是一個提速的工具,因為要執行編譯為本機代碼必須還是要原程式集,而原程式集中存在MSIL,是以讓程式無法脫離被反編譯的目地。 大家回家,如果有空,可以做做試驗。 Ngen /show 就可以看到緩存中所有的已編譯好的程式集,是以Dotnet并不慢。

Ngen <assembly path or display name> 可以把指定程式集映象為本機代碼。 Ngen /? 可以看到其它參數   以上是ms提供的工具,下在講講,自己在程式設計的過程中,如何使用技巧來防止破解或反編譯。

  1. 程式設計技巧保護方案

在這裡,我會給大家介紹兩種三種方式 1.       人為混淆 在這裡,我就要先簡單的講講什麼叫做混淆 混淆顧名思意,就是混亂,不明确的意思。MetaData中都有一個Rid,程式集運作時就已經和名稱沒什麼關系了,都使用Rid來調用的,是以可以将名稱省去。 什麼叫人為混淆呢,就是人為的制造混淆。 曾經看過一個程式集,手工的将一個Method折成幾十個或上百個,進而達到讓你看不懂的目的。不過可惜的說一句:現在的Dotnet程式集的分析工具都很強大,正引用,反調用都可以用程式來實作,是以即實這麼做,了沒多大用處。著名的Reflector就有這些功能。 2.       隐藏程式集 剛剛談到了Reflector,它就是使用這種方式來隐藏自己的核心程式集的。相信我,Reflector并不是您看到的那一個可執行程式,它的可執行程式隻是一個殼而以,裡面是一個定義和接口,沒有執行個體的方法。如果你想得到他是怎樣反編譯的核心,恐怕你會在它這個迷宮中迷失方向。 它是怎樣做的呢?讓我來告訴你,它的核心程式集事實上就是它的一個資源。而這個資源是一個加密的資源。如果我沒記錯,他應該是在輕按兩下第一個需要反編譯的Method的時候開始釋放這個資源,并對資源解密然後動态的加載。這樣做的優點核心程式集是不會在硬碟上留下任何痕迹的,它隻解在記憶體中解密并被加載,你基本上無法得到這個程式集。而且Dotnet是不允許記憶體 Dump的。 大家是不是覺得這種保護方法不錯呢?你可以把你的核心代碼加密後做成資源包在程式裡,在使用的時候再解密出來,這隻需要你自己去實作就可以了。 不過我還得說句負責任的話,如果你有精力,并且很有耐心和技術,相信你還是可以在幾天時間内找出它的核心程式集解密算法的位置。并成功的解出它的資源程式集。 如果是高手又非常有經驗,這種方式的加密手段應該是秒殺。   3.       将程式集中的相關Method(方法)編譯成Unmanaged(非托管代碼) 下面介紹的内容是不管你是菜鳥,或是高手,都無法得到核心代碼的方 它可稱之為終極的保護手段,因為它就是“非托管代碼”。 什麼是托管代碼,什麼是非托管代碼。 簡單的說,托管代碼就是需要Jit去解釋的中間語言代碼,而非托管代碼 就是本機代碼。下面要介紹的方式就是教您如何在自己的程式集中即擁有托管代碼,又擁有非托管代碼。注意,非托管代碼是無法被現在的反編譯工具反編譯的。        特别注意一點,我沒有自己試過,但我看人做過,并得到了證明。        在Dotnet程式集中,允許托管代碼和非托管代碼共存,怎樣實作呢?這并不是無償的,這是需要條件的。它的條件就是必須使用VC++.NET非托管方式來寫dll,再用VC++托管方式建立工程引入這個本機代碼的dll。最終生成一個Dotnet程式集的dll。那麼這個程式集裡面即有托管代碼,又有非托管代碼。托管代碼是可以反編譯的,而非托管代碼不可能被反編譯。 有人可能要問了,這和自己用VC++寫個dll有什麼差別?差別就是這樣的結合更緊密一些,而且也不能用正常的分析Asm的工具去分析這個dll。 這裡還要解釋一個誤解,有人說,利用Win32的本機代碼寫注冊算法,并生成dll供給Dotnet程式集調用,防止破解。其實這句話隻說對了一半,這隻能增加破解注冊機的難度,并防止不了破解。為什麼呢?因為注冊對不對還是要在Dotnet程式集中進行判斷,是以,隻要改掉這個判斷,一樣達到了破解效果。但是如果要分析注冊算法,那可就是困難了一些了。

  1. 第三方保護工具

下面,我們講一講第三方的保護工具和概念 第三方保護工具較好的廠商有: 1.       Aiasted.SOFT        a)         産品 :MaxtoCode ,種類 :加密、混淆 2.       PerEmptive Solutions      a)         産品 :Dotfuscator Community ,種類 :混淆 3.       Remotesoft a)         産品 :Remotesoft Protect ,種類 :加密 b)        産品 :Remotesoft Dotfuscator ,種類 :混淆 4.       XenoCode a)         産品 :XenoCode ,種類:混淆 5.       其它的一些公司,最近上海有一款公司出了國内第一款混淆工具,如果大家要選擇混淆産品的話,支援一下國産也不錯。   第三方工具的保護方式分類 1.       混淆 ? 這是目前最流行的方式吧。今天我們就來做個剖析。讓大家去衡量一下混淆的強度如何。 混淆軟體一般都有三個功能 1.         字元串加密 2.         名稱混淆 3.         流程混淆 目前流行的混淆軟體有        XenoCode、Dotfuscator、Remotesoft,MaxtoCode裡也內建了少許混淆功能。 利用幻燈片講解流程混淆原理 利用程式當場示範如何反流程混淆   1.目标程式 2.被混淆的程式使用 Reflector 檢視 3.使用Ildasm反編譯出 IL 檔案        ildasm XenoCodeTest.exe /out=XenoCodeTest.il 4.将IL 檔案中的某個方法抽出 5.使用 Deflow 進行反混淆 6.回填,并使用 Ilasm 進行編譯 Ilasm XenoCodeTest.il /resource=XenoCodeTest.res /output=XenoCodeTestNew.exe 7.再回到 Reflector 中進行檢視   2.       打包 ? ThInstall 是一個打包工具,他可以打包幾乎所有的應用程式,也包括 Dotnet。 他将多個Dotnet程式集包在一個大程式裡,達到無法反編譯的目地。不過想想也知道,即然是打包,在需要運作時肯定會釋放,如果找到了釋放出來的檔案,就跟沒保護一樣了,是以,這算是一個最爛的保護手段。當然,本來我沒想把它列進來的,是因為看到論壇上經常有人用這個Thinstall回複别人說可以保護Dotnet程式集,是以我才特别忠告大家,别信。   3.       加密 ? 加密保護并不同于混淆,它是目前最好的保護方式,也是保護能力最強的。 他把Dotnet的先天不足在一定程度上大幅提高,為Dotnet引來更多的開發者。加密保護的軟體都有一個共同點,即把Dotnet的反編譯引深到Win32的反彙編中了,可惜的是,也限制了Dotnet跨平台的優勢。 此類的代表軟體有 MaxtoCode  、Remotesoft protect ,其它的一些國外的,我就不說了,實 在讓人用不下去。 由于Remotesoft公司過于小氣,Protect連試用版都不提供,是以我隻能找到他的一個加密過的産品 WebGrid3.5,但WebGrid4.0就未用Protect了,不知道為什麼,幾千美金就這麼廢了?分析WebGrid3.5以後,發現他和MaxtoCode一樣,産生的結果就是看不到IL代碼了,而且也會生成一個本機代碼的DLL作為運作環境。 由于對Remotesoft Protect無法深入研究,隻知道效果和MaxtoCode一樣,那麼我們就來講講MaxtoCode的實作原理吧。 MaxtoCode是為了迷補Dotnet的先天性不足而出世的。它是中國第一款高強度的Dotnet保護軟體,在世界的Dotnet保護水準線上也處于優勢性的領先。 其實MaxtoCode的原理很簡單,它是将程式集中所有的IL進行加密,是以使用反編譯器無法看到IL,進而不能進行反編譯。基于Framework提取Method的IL作為基礎原理,當JIT需要IL時,我就将加過密的IL解密給JIT去編譯,這樣就形成了MaxtoCode的基本原理。         

繼續閱讀