Android教程網
  1. 首頁
  2. Android 技術
  3. Android 手機
  4. Android 系統教程
  5. Android 游戲
 Android教程網 >> Android技術 >> 關於Android編程 >> Android apk 混淆代碼(遇到的各種坑和解決方案)

Android apk 混淆代碼(遇到的各種坑和解決方案)

編輯:關於Android編程

以前做的手機項目,並沒有要求混淆,一直沒時間去看,等到做了平板,有混淆的需求才要硬著頭皮去看混淆到底是如何工作的,以及如何混淆驗證成功,參考一篇博客,講的非常詳細,而且每一步都寫的非常好,再次感謝作者的辛勤勞作:關鍵是要先准備好兩個工具,細節這篇博客講到了,我說下我遇到的坑和問題:

1.dex2jar工具(下載地址:http://code.google.com/p/dex2jar/),開源的反編譯的項目,可以將apk文件轉成一個jar包

2.jd-gui工具(下載地址:http://jd-gui.softpedia.com/)。這個工具挺厲害的,可以將jar包反編譯成具體的java代碼

=================分割線========================正式混淆工作有可能遇到的問題如下======================================

一.准備好了這些工作,就可以開始進行混淆的工作了,第一步,當然是找到你的android工程,按照上面的連接,給工程添加混淆的設置,如下圖:\

這一步有可能你在project.properties文件如何添加混淆的文件,一共有兩種方式,一種是新建一個proguard.cfg這種方式我沒試過,不過高版本的sdk,建議還是使用proguard-project.txt每個工程默認都會有一個. 需要注意的是你需要在環境變量裡面添加sdk的工程目錄,如下圖:

\

 

二.上述前期工作准備好後,就要在proguard-project.txt文件裡面新建混淆的規則了,一般的原則是在libs的第三方jar需要保留,不進行混淆,默認的一些谷歌官方建議保留的activity也是需要保留的,這些文檔都有,如下圖我的工程裡面的jar包,第一次進行簽名打包時候,就遇到下面這麼多錯誤:

 

[2016-08-17 18:33:40 - VerBank-APadClientStation] Proguard returned with error code 1. See console
[2016-08-17 18:33:40 - VerBank-APadClientStation] Note: there were 1637 duplicate class definitions.
[2016-08-17 18:33:40 - VerBank-APadClientStation] Warning: allone.MTP.VerBank01.Ctrl.comm.ipop.CtrlServerIPFather: can't find superclass or interface allone.MTP.VerBank01.comm.IPOP.IPFather
[2016-08-17 18:33:40 - VerBank-APadClientStation] Warning: allone.MTP.VerBank01.Ctrl.comm.ipop.CtrlServerOPFather: can't find superclass or interface allone.MTP.VerBank01.comm.IPOP.OPFather
[2016-08-17 18:33:40 - VerBank-APadClientStation] Warning: allone.MTP.VerBank01.Ctrl.comm.ipop.csts.CtrlCSTSIPFather: can't find superclass or interface allone.MTP.VerBank01.comm.IPOP.IPFather


[2016-08-17 18:33:40 - VerBank-APadClientStation] Warning: allone.MTP.VerBank01.Ctrl.comm.ipop.csts.CtrlCSTSIPFather: can't find referenced class allone.MTP.VerBank01.comm.IPOP.IPFather
[2016-08-17 18:33:40 - VerBank-APadClientStation] Warning: allone.MTP.VerBank01.Ctrl.comm.ipop.csts.CtrlCSTSIPFather: can't find referenced class allone.MTP.VerBank01.comm.IPOP.IPFather

[2016-08-17 18:33:40 - VerBank-APadClientStation] Warning: allone.crypto.RSA.RSACrypt: can't find referenced class sun.security.rsa.RSAPublicKeyImpl
[2016-08-17 18:33:40 - VerBank-APadClientStation] Warning: allone.crypto.RSA.RSACrypt: can't find referenced class sun.security.rsa.RSAPublicKeyImpl
[2016-08-17 18:33:40 - VerBank-APadClientStation] Warning: allone.crypto.RSA.RSACrypt: can't find referenced class sun.security.rsa.RSAPublicKeyImpl

[2016-08-17 18:33:40 - VerBank-APadClientStation] Warning: com.google.android.gcm.server.Sender: can't find referenced class org.json.simple.JSONValue
[2016-08-17 18:33:40 - VerBank-APadClientStation] Warning: com.google.android.gcm.server.Sender: can't find referenced class org.json.simple.parser.JSONParser


[2016-08-17 18:33:40 - VerBank-APadClientStation] Warning: com.sun.mail.imap.protocol.IMAPSaslAuthenticator: can't find referenced class javax.security.sasl.Sasl
[2016-08-17 18:33:40 - VerBank-APadClientStation] Warning: com.sun.mail.imap.protocol.IMAPSaslAuthenticator: can't find referenced class javax.security.sasl.SaslException
[2016-08-17 18:33:40 - VerBank-APadClientStation] Warning: com.sun.mail.imap.protocol.IMAPSaslAuthenticator: can't find referenced class javax.security.sasl.SaslClient
[2016-08-17 1

我只列出了一部分,總共有1400行,看到這些你是不是下了一大跳,警告也是無法順利導出jar包,所以還得硬著頭皮解決,其實吧,沒那麼恐怖,看到上面的總說找不到的警告,你可以將這些類告訴混淆工具不要進行警告,這樣就能避免很多的錯誤,如下我的解決方式,(注:其實就是警告什麼,就告訴它不要警告,寫出來具體的路徑和類名)

 

 

-libraryjars libs/activation.jar
-libraryjars libs/armeabi/libtwcajniV10100U20150115.so
-libraryjars libs/additionnal.jar
-libraryjars libs/commons-codec-1.3.jar
-libraryjars libs/gcm-server.jar
-libraryjars libs/gcm.jar
-libraryjars libs/javax.mail.jar
-libraryjars libs/nineoldandroids-2.4.0.jar
-libraryjars libs/TWCAcMobileAPI.jar
-libraryjars libs/VerBank-CSTSv3-ClientAPI.jar

-dontwarn  allone.**
-dontnote  allone.**
-keep class allone.**{*;}

-dontwarn  jedi.**
-dontnote  jedi.**
-keep class jedi.**{*;}

-dontwarn  debug.**
-dontnote  debug.**
-keep class debug.**{*;}


-dontwarn org.apache.log4j.lf5.viewer.**
-dontnote org.apache.log4j.lf5.viewer.**

-dontwarn com.sun.mail.**
-dontnote com.sun.mail.**

-dontwarn  com.google.android.gcm.**
-dontnote  com.google.android.gcm.**

-dontwarn  sun.security.rsa.RSAPublicKeyImpl
-dontnote  sun.security.rsa.RSAPublicKeyImpl







-dontwarn sun.misc.Unsafe
-dontwarn com.google.common.collect.MinMaxPriorityQueue
-dontwarn javax.swing.**
-dontwarn java.awt.**
-dontwarn org.jasypt.encryption.pbe.**
-dontwarn java.beans.**
-dontwarn org.joda.time.**
-dontwarn com.google.android.gms.**
-dontwarn org.w3c.dom.bootstrap.**
-dontwarn com.ibm.icu.text.**
-dontwarn demo.**

注注注:重要的事情說三遍,你也許將很多警告去掉了,但簽名打包完成,以為可以順利運行了,沒想到一旦使用到第三方的jar包,程序就奔潰,我分析就是混淆工具將我的第三方的一些類也進行混淆了,導致無法識別,所以呢,我們需要將第三方路徑上的class都保留,不要進行混淆如下:

 

 

-libraryjars libs/VerBank-CSTSv3-ClientAPI.jar   //這裡這樣寫雖然說是不混淆,但我測試發現,有些類還是混淆了,所以才會寫下面的保持類不混淆的寫法

-dontwarn  allone.**
-dontnote  allone.**  //注意**和**{*;}的區別, -keep class allone.**這樣只能保留一層文件夾,如果下面有好多文件夾需要保留,需要攜程**{*;}這是我實驗出來,由於缺少必要的資料,這個坑試了好久才發現.
-keep class allone.**{*;}

-dontwarn  jedi.**
-dontnote  jedi.**
-keep class jedi.**{*;}

-dontwarn  debug.**
-dontnote  debug.**
-keep class debug.**{*;}

這裡有一個很大的坑就是:使用-libraryjars libs/第三方jar包,在運行的時候,使用這個第三方類還是會報錯,我只能使用keep 寫上具體出錯的類,然後解決了這個問題:
注意**和**{*;}的區別, -keep class allone.**這樣只能保留一層文件夾,如果下面有好多文件夾需要保留,需要攜程**{*;}這是我實驗出來,由於缺少必要的資料,這個坑試了好久才發現.

 

三,以下是我工程完整的proguard-project.txt,你需要結合自己使用到的工程jar包,和具體的報錯信息,進行處理就可以了,總體的原則就是那裡出錯,就告訴他不要再警告,如果第三方達成jar包還是有錯的話,就將第三方具體的類和class路徑所有的類都keep,不進行混淆,這樣之後就不會有問題,文件如下:

 

# To enable ProGuard in your project, edit project.properties
# to define the proguard.config property as described in that file.
#
# Add project specific ProGuard rules here.
# By default, the flags in this file are appended to flags specified
# in ${sdk.dir}/tools/proguard/proguard-android.txt
# You can edit the include path and order by changing the ProGuard
# include property in project.properties.
#
# For more details, see
#   http://developer.android.com/guide/developing/tools/proguard.html

# Add any project specific keep options here:

# If your project uses WebView with JS, uncomment the following
# and specify the fully qualified class name to the JavaScript interface
# class:
#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
#   public *;
#}

-optimizationpasses 5   
#混淆時不會產生形形色色的類名   
-dontusemixedcaseclassnames
-dontskipnonpubliclibraryclasses
#//指定不去忽略非公共的類庫   
-dontpreverify
#//不預校驗   
-verbose   
-optimizations !code/simplification/arithmetic,!field/*,!class/merging/*//優化   


-libraryjars libs/activation.jar
-libraryjars libs/armeabi/libtwcajniV10100U20150115.so
-libraryjars libs/additionnal.jar
-libraryjars libs/commons-codec-1.3.jar
-libraryjars libs/gcm-server.jar
-libraryjars libs/gcm.jar
-libraryjars libs/javax.mail.jar
-libraryjars libs/nineoldandroids-2.4.0.jar
-libraryjars libs/TWCAcMobileAPI.jar
-libraryjars libs/VerBank-CSTSv3-ClientAPI.jar

-dontwarn  allone.**
-dontnote  allone.**
-keep class allone.**{*;}

-dontwarn  jedi.**
-dontnote  jedi.**
-keep class jedi.**{*;}

-dontwarn  debug.**
-dontnote  debug.**
-keep class debug.**{*;}


-dontwarn org.apache.log4j.lf5.viewer.**
-dontnote org.apache.log4j.lf5.viewer.**

-dontwarn com.sun.mail.**
-dontnote com.sun.mail.**

-dontwarn  com.google.android.gcm.**
-dontnote  com.google.android.gcm.**

-dontwarn  sun.security.rsa.RSAPublicKeyImpl
-dontnote  sun.security.rsa.RSAPublicKeyImpl







-dontwarn sun.misc.Unsafe
-dontwarn com.google.common.collect.MinMaxPriorityQueue
-dontwarn javax.swing.**
-dontwarn java.awt.**
-dontwarn org.jasypt.encryption.pbe.**
-dontwarn java.beans.**
-dontwarn org.joda.time.**
-dontwarn com.google.android.gms.**
-dontwarn org.w3c.dom.bootstrap.**
-dontwarn com.ibm.icu.text.**
-dontwarn demo.**


-libraryjars libs/Android-support-v4.jar
-dontwarn android.support.v4.**
-keep class android.support.**{*;}
-keep interface android.support.v4.app.**{*;}
-keep public class * extends android.support.v4.**
-keep public class * extends android.app.Fragment

   
#不進行混淆保持原樣      
-keep public class * extends android.app.Activity 
-keep public class * extends android.app.Application 
-keep public class * extends android.app.Service 
-keep public class * extends android.content.BroadcastReceiver 
-keep public class * extends android.content.ContentProvider 
-keep public class * extends android.app.backup.BackupAgentHelper 
-keep public class * extends android.preference.Preference 
-keep public class com.android.vending.licensing.ILicensingService 

-keepattributes Signature
-keepattributes *Annotation*
-keep class **.R$* { *; }



 
-keepclasseswithmembernames class * {
native ;
}
-keepclasseswithmembers class * {
public (android.content.Context, android.util.AttributeSet);
}
-keepclasseswithmembers class * {
public (android.content.Context, android.util.AttributeSet, int);
}
-keepclassmembers class * extends android.app.Activity {
public void *(android.view.View);
}
-keepclassmembers enum * {
public static **[] values();
public static ** valueOf(java.lang.String);
}
-keep class * implements android.os.Parcelable {
public static final android.os.Parcelable$Creator *;
}

最後的結果截圖如下:\

花了好長時間終於解決了,過程雖然很艱辛,但是解決了,歡迎拍磚,有問題可以問我,很高興為你解答.

  1. 上一頁:
  2. 下一頁:
熱門文章
閱讀排行版
Copyright © Android教程網 All Rights Reserved