日韩久久久精品,亚洲精品久久久久久久久久久,亚洲欧美一区二区三区国产精品 ,一区二区福利

Jocky混淆JAVA代碼(保護你的JAVA項目)

系統 2066 0

原帖中沒有給出jocky的相關jar,我從某個地方下載到了jocky的相關jar,并在項目中得到了很好的應用,在這里共享下。

一、前言

1.1 什么是Jocky?

???我們知道,Java是一種跨平臺的編程語言,其源碼(.java文件)被編譯成與平臺無關的字節碼(.class文件),然后在運行期動態鏈接。這樣,編譯后的類文件中將包含有符號表,從而使得Java程序很容易被反編譯。相信每一個Java開發人員,都曾經用過諸如Jad之類的反編譯器,對Java的class 文件進行反編譯,從而觀察程序的結構與實現細節。如此一來,對于那些需要嚴格進行知識產權保護的Java應用,如何有效的保護客戶的商業投資,是開發人員經常需要面對的問題。
???于是就出現了Java混淆編譯器,它的作用是打亂class文件中的符號信息,從而使反向工程變得非常困難。
???Jocky就是這樣一款優秀的Java混淆編譯器。

1.2 為什么需要Jocky?

???目前業界有不少商業的甚或是開源的混淆編譯器,但它們普遍存在一些這樣或者那樣的問題。一般而言,現有的混淆器都是對編譯好的 class文件進行混淆,這樣就需要編譯和混淆兩個步驟。而事實上,并不是所有的符號都需要混淆。如果你開發的是一個類庫,或者某些類需要動態裝載,那些公共API(或者說:那些被publish出來的API)就必須保留符號不變,只有這樣,別人才能使用你的類庫。現有的混淆器提供了GUI或腳本的方式來對那些需要保留的符號名稱進行配置,但如果程序較大時,配置工作將變得很復雜,而程序一旦修改,配置工作又要重新進行。某些混淆器能夠調整字節碼的順序,使反編譯更加困難,但筆者經歷過混淆之后的程序運行出錯的情況。
???而Jocky與其它混淆編譯器最大的不同之處在于:它是直接從源碼上做文章,也就是說編譯過程本身就是一個混淆過程。

1.3 Jocky是如何工作的?

???Jocky混淆編譯器是在Sun JDK中提供的Java編譯器(javac)的基礎上完成的,修改了其中的代碼生成過程,對編譯器生成的中間代碼進行混淆,最后再生成class文件,這樣編譯和混淆只需要一個步驟就可以完成。另外可以在源程序中插入 符號保留指令 來控制哪些符號需要保留,將混淆過程與開發過程融合在一起,不需要單獨的配置。

1.4 Jocky的作用

1.4.1代碼混淆

???如前文所述,混淆編譯是Jocky的首要用途。我們舉一個最簡單的例子,下面的SimpleBean是未經混淆的class文件通過Jad反編譯以后獲得的源文件:

?1 public ? class ?SimpleBean? implements ?Serializable? {
?2 ??
?3 ?? private ?String?name? = ? " myname " ;
?4 ??
?5 ?? private ?List?myList? = ? null ;
?6 ??
?7 ?? public ? void ?SimpleBean()? {
?8 ????myList? = ? new ?ArrayList( 10 );
?9 ??}

10
11 ?? public ? void ?foo1()? {
12 ????myList.add( " name " );
13 ??}

14 ??
15 ?? private ? void ?foo2()? {????
16 ??}

17 ??
18 ?? private ? void ?writeObject(java.io.ObjectOutputStream?out)
19 ?????? throws ?IOException? {
20 ????
21 ??}

22
23 }
?
<未混淆的類文件反編譯后的效果>


???下面是經Jocky混淆過的類文件,通過Jad反編譯后產生的源文件:

?1 public ? class ?SimpleBean? implements ?Serializable? {
?2
?3 ?? private ?String?_$ 2 ;
?4
?5 ?? private ?List?_$ 1 ;
?6
?7 ?? public ?SimpleBean()????? {
?8 ????????_$ 2 ? = ? " myname " ;
?9 ???????? this ;
10 ????????JVM?INSTR? new ?# 4 ??? < Class?ArrayList > ;
11 ????????JVM?INSTR?dup?;
12 ????????JVM?INSTR?swap?;
13 ???????? 10 ;
14 ????????ArrayList();
15 ????????_$ 1 ;
16 ????}
??
17 ?? public ? void ?foo1()? {
18 ????_$ 1 .add( " name " );
19 ??}

20
21 ?? private ? void ?_$ 1 ()? {
22 ??}

23
24 ?? private ? void ?writeObject(ObjectOutputStream?objectoutputstream) {
25 ?????? throws ?IOException? {
26 ??}

27 }
?
<Jocky混淆過的類文件反編譯的效果>

?

1.4.2 支持將JDK 5.0的語法編譯成能夠在JDK 1.4上運行的類文件

???JDK 5.0在語法層面上有許多新增特色,能夠為簡化應用的開發帶來一些便利。譬如Generics、Enhanced for Loop以及 Autoboxing/Unboxing等。但另人遺憾的是,倘若利用這些新的語法開發應用,就意味著不能夠在JDK 1.4上運行,而JDK 1.4畢竟是目前最為普及的VM版本。幸運是,Jocky的另一個特色就是:通過參數配置,能夠把用JDK 5.0語法編寫的應用編譯成JDK 1.4上的類文件版本。我們可以把經過 Jocky編譯的類文件以UltraEdit打開,可以發現在第8個字節上(類文件的major version)的數值是0x30,即十進制的48,這是JDK 1.4所能夠理解的類文件版本(JDK 5.0默認編譯的類文件版本是49)。前提是:應用中不能夠使用JDK 1.4中所沒有的一些API。

二、Jocky的用法

2.1 常規用法

???使用Jocky非常簡單,獲得jocky.jar以后,只需要運行java -jar jocky.jar就可以啟動Jocky混淆編譯器,jocky的命令行參數和javac完全相同,但增加了一個新的參數-scramble,它的用法如下:

    
-scramble??????????混淆所有package?private或private符號 -scrambleall???????混淆所有符號 -scramble: < level > ??混淆相應級別的符號 其中 < level > 指定混淆級別,可以是以下幾種級別: -scramble:none????????不進行混淆 -scramble:private?????對所有private訪問級別的元素進行混淆 -scramble:package?????對所有private或package?private元素進行混淆 -scramble:protected???對所有private,?package?private,?protected元素進行混淆 -scramble:public??????對所有的元素都進行混淆 -scramble:all?????????相當于-scramble:public 如果使用-scramble不帶級別參數,則相當于-scramble:package

2.2 Jocky for Ant

????近年來,Ant已經成為Java應用開發中打包工具的事實上的標準。在應用的開發過程中,我們往往都會有一個Ant腳本,通過該腳本,能夠對應用進行編譯、打包、發布等一系列過程。因此,Jocky的最佳切入點便是對Ant的支持。
????在Ant中使用Jocky非常簡單:

????1. 將lib\jocky-ant.jar copy至ANT_HOME\lib目錄下。

????2. 在ant腳本中加入這樣一行代碼,以引入Jocky Task

??
????? < taskdef? resource ="jockytasks/" > ?


????3. 設置Jocky的一些基本屬性,包括: jocky.jar包的位置,以及混淆級別,如下所示:

????
??? < jocky? jar ="?F:\Works2\Jocky\jocky1.0\lib\jocky.jar" ?enable ="true" ?level ="private/" > ?


????4. 當設置jocky的enable屬性為true時,此時,Ant腳本中的javac編譯命令,便會被自動替換成Jocky編譯器;當設置enable屬性為false時,javac編譯命令將恢復成正常設置,示例腳本如下:

?1 < project? name ="jocky" ?default ="build" > ?
?2 <!-- ?引入Jocky?Ant?Task,要確保jocky-ant.jar位于ANT_HOME\lib目錄下? -->
?3 < taskdef? resource ="jockytasks" > ? </ taskdef >
?4 < target? name ="build" > ?
?5 <!-- ?設置jocky.jar的位置以及混淆級別,當enable為true時,javac?task將被自動替換成Jocky混淆編譯器? -->
?6 < jocky? jar ="?F:\Works2\Jocky\jocky1.0\lib\jocky.jar" ?enable ="?true" ?level ="?private" > ? </ jocky > ?
?7 <!-- ?下面的編譯,將使用Jocky混淆編譯器? -->
?8 < javac? destdir ="bin2" ?debug ="on" ?source ="1.5" ?target ="1.4" > ?
?9 < src? path ="src" ></ src >
10 </ javac >
11 <!-- ?當enable為false時,javac?task將被恢復成正常設置,?Jocky編譯器不再起作用? -->
12 < jocky? enable ="false" ></ jocky >
13 <!-- ?下面的編譯,將使用正常的Javac編譯器? -->
14 < javac? destdir ="bin3" ?debug ="on" ?target ="1.4" > ?
15 < src? path ="src" ></ src >
16 </ javac >
17 </ target >
18 </ project >
<Jocky的Ant腳本示例>


????注意: Jocky for Ant在Ant 1.6.5上開發,推薦使用該版本。

2.3 Jocky for Eclipse

????Jocky提供了Eclipse的插件,從而能夠直接在Eclipse中使用Jocky。
????1. Jocky插件的安裝:
????將Jocky插件安裝至Eclipse中非常簡單,只需要將eclipse/plugins/org.apusic.jocky_1.0.0目錄 copy 至 Eclipse的 plugins目錄即可。或者在Eclipse/links文件夾中,通過link方式指定Jocky的插件目錄。

????2. 在Eclipse中使用Jocky:
????在Eclipse中使用Jocky也非常簡單,任何一個Java工程,選中工程通過右鍵菜單,都可以出現Jocky的快捷菜單:

? Jocky混淆JAVA代碼(保護你的JAVA項目)
<Jocky在Eclipse中的右鍵菜單>


? Jocky混淆JAVA代碼(保護你的JAVA項目)
<Jocky在Eclipse中的屬性設置>



????事實上,在Eclipse中使用Jocky時,Jocky也是首先針對所選工程生成Ant的Build文件(默認名稱jocky_build.xml),然后再通過Ant完成混淆編譯。

????以下是Jocky在Eclipse中自動生成的Ant Build 文件示例:

?1 < project? basedir ="." ?default ="build" ?name ="jocky.example.jocky" > ?
?2 < property? name ="jocky.jar" ?value ="f:\EclipseWTP1.0.8\workspace_jdk5_apusicstudio\org.apusic.jocky\jocky.jar" ></ property >
?3 < property? name ="jocky.output.dir" ?value ="jocky" ></ property >
?4 < property? name ="jocky.scramble.level" ?value ="package" ></ property >
?5 < property? name ="target" ?value ="1.4" ></ property >
?6 < path? id ="project.classpath" > ?
?7 < pathelement? location ="bin" ></ pathelement >
?8 </ path >
?9 < target? name ="init" > ?
10 < jocky? jar ="${jocky.jar}" ?level ="${jocky.scramble.level}" ></ jocky >
11 < mkdir? dir ="${jocky.output.dir}" ></ mkdir >
12 < mkdir? dir ="${jocky.output.dir}/bin" ></ mkdir >
13 </ target >
14 < target? name ="clean" > ?
15 < delete? dir ="${jocky.output.dir}/bin" ></ delete >
16 < delete? dir ="${jocky.output.dir}" ></ delete >
17 </ target >
18 < target? depends ="init" ?name ="build" > ?
19 < echo? message ="${ant.project.name}:?${ant.file}" ></ echo >
20 < jocky? enable ="true" ></ jocky >
21 < javac? destdir ="${jocky.output.dir}/bin" ?target ="${target}" > ?
22 < src? path ="src" ></ src >
23 < classpath? refid ="project.classpath" ></ classpath >
24 </ javac >
25 </ target >
26 </ project >
<Jocky在Eclipse中自動生成的Ant腳本示例>


注1:只支持Eclipse 3.1.1及以上版本。
注2:如果在Eclipse中找不到Jocky插件,請刪除 Eclipse安裝目錄/configuration/org.eclipse.update 文件夾 (Maybe an eclipse bug?)。

2.4 如何使用符號保留指令

???除了在命令行用 -scramble 參數控制符號混淆級別外,還可以在源代碼中使用符號保留指令來控制那些符號需要保留。符號保留指令是一個Java文檔注釋指令,可以插入在類和類成員的文檔注釋中,例如:

?1 /**
?2 ?*?This?class?should?preserve.
?3 ?*?@preserve
?4 ?*/
?5 public?class?Foo?{
?6 ????/**
?7 ?????*?You?can?specify?which?field?should?be?preserved.
?8 ?????*?@preserve
?9 ?????*/
10 ????private?int?x;
11
12 ????/**
13 ?????*?This?field?is?not?preserved.
14 ?????*/
15 ????private?int?y;
16
17 ????/**
18 ?????*?You?can?also?preserve?methods.
19 ?????*?@preserve
20 ?????*/
21 ????public?void?hello()?{}
22
23 ????/**
24 ?????*?This?method?is?not?preserved.
25 ?????*/
26 ????private?void?collect()?{}
27 }?
<使用preserved指令的示例>


???如果沒有@preserve指令,則根據混淆級別及成員的訪問級別來確定符號是否保留。
???對于類的符號保留指令可以附帶一個保留級別參數,來控制類成員的符號保留,包括:

    
@preserve????????????僅對類名進行保留,類成員的保留根據-scramble命令行參數決定 @preserve?public?????保留所有public成員 @preserve?protected??保留所有public和protected成員 @preserve?package????保留所有public,?protected,?package?private成員 @preserve?private????保留所有成員 @preserve?all????????相當于@preserve?private

???事實上,即便不加@preserve指令,Jocky對Java語言特有的一些private級別的方法不進行混淆,譬如,在序列化時有特殊作用的writeObject及readObject方法等。但筆者強烈建議: 針對這些有特殊含義不能夠被混淆的 private級別的方法或者字段,請以@preserve指令予以保護。

注1:建議通過IDE的JavaDoc設置,來輔助@preserve指令的書寫。

三、Jocky的限制

???正如前文所說,Jocky是基于源代碼的混淆編譯器,因此,Jocky不支持分別編譯,必須對所有的源文件同時進行混淆編譯。但事實上,倘若混淆級別控制在private級別上,該限制便不復存在。

Jocky混淆JAVA代碼(保護你的JAVA項目)


更多文章、技術交流、商務合作、聯系博主

微信掃碼或搜索:z360901061

微信掃一掃加我為好友

QQ號聯系: 360901061

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

【本文對您有幫助就好】

您的支持是博主寫作最大的動力,如果您喜歡我的文章,感覺我的文章對您有幫助,請用微信掃描上面二維碼支持博主2元、5元、10元、自定義金額等您想捐的金額吧,站長會非常 感謝您的哦!!!

發表我的評論
最新評論 總共0條評論
主站蜘蛛池模板: 罗平县| 陵川县| 石嘴山市| 磐安县| 南康市| 彭山县| 湟中县| 通许县| 承德市| 西乡县| 云南省| 措勤县| 洞头县| 雷州市| 梨树县| 江阴市| 九龙城区| 乐都县| 同德县| 苏州市| 龙州县| 赞皇县| 巩义市| 稷山县| 霍山县| 宜都市| 称多县| 措勤县| 平江县| 安龙县| 南涧| 阿克陶县| 内丘县| 三明市| 尚志市| 延寿县| 新安县| 广平县| 涟源市| 松江区| 达日县|