混淆作用
将程序变得难以阅读,防范程序被逆向。
Android Studio开启混淆的方法
Android Studio自身集成Java语言的ProGuard作为压缩,优化和混淆工具,可以配合Gradle构建工具使用。找到gradle里的minifyEnabled设置为true即可。
android {
...
buildTypes {
release {
minifyEnabled true
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
}
}
以上示例代码表示对release版本混淆。
ProGuard作用
压缩 (Shrinking)
默认开启,以减少应用体积,移除未被使用的类和成员,并且会在优化动作执行之后再执行(因为优化后可能会再次暴露一些未被使用的类和成员)
-dontshrink 关闭压缩
优化(Optimization)
默认开启,在字节码级别执行优化,让应用运行的更快。
-dontoptimize 关闭优化
-optimizationpasses n 表示proguard对代码进行迭代优化的次数,Android一般为5
混淆(Obfuscation)
默认开启,增大反编译难度,类和类成员会被随机命名,除非用keep保护
dontobfuscate 关闭混淆
混淆后默认会在工程目录
app/build/outputs/mapping/release下生成一个mapping.txt文件,这就是混淆规则,我们可以根据这个文件把混淆后的代码反推回源本的代码,所以这个文件非常重要。
有时候混淆后会报错,可能要对部分避免混淆。
(1)
-keep class cn.hadcn.test.**
-keep class cn.hadcn.test.*
其中一颗星表示只保持该包下的类名
两颗星表示把本包和所含子包下的类名都保持。
(2)
-optimizationpasses 5 # 指定代码的压缩级别
-dontusemixedcaseclassnames # 是否使用大小写混合
-dontskipnonpubliclibraryclasses # 是否混淆第三方jar
-dontpreverify # 混淆时是否做预校验
-verbose # 混淆时是否记录日志
-optimizations !code/simplification/arithmetic,!field/*,!class/merging/* # 混淆时所采用的算法
-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 # 保持哪些类不被混淆
-keepclasseswithmembernames class * { # 保持 native 方法不被混淆
native <methods>;
}
-keepclasseswithmembers class * { # 保持自定义控件类不被混淆
public <init>(android.content.Context, android.util.AttributeSet);
}
-keepclasseswithmembers class * {
public <init>(android.content.Context, android.util.AttributeSet, int); # 保持自定义控件类不被混淆
}
-keepclassmembers class * extends android.app.Activity { # 保持自定义控件类不被混淆
public void *(android.view.View);
}
-keepclassmembers enum * { # 保持枚举 enum 类不被混淆
public static **[] values();
public static ** valueOf(java.lang.String);
}
-keep class * implements android.os.Parcelable { # 保持 Parcelable 不被混淆
public static final android.os.Parcelable$Creator *;
}
-keep class MyClass; # 保持自己定义的类不被混淆
guillep PullToRefresh
-optimizationpasses 5
-dontusemixedcaseclassnames
-dontskipnonpubliclibraryclasses
-dontpreverify
-verbose
-optimizations !code/simplification/arithmetic,!field/*,!class/merging/*
-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
-keepclasseswithmembernames class * {
native <methods>;
}
-keepclasseswithmembernames class * {
public <init>(android.content.Context, android.util.AttributeSet);
}
-keepclasseswithmembernames class * {
public <init>(android.content.Context, android.util.AttributeSet, int);
}
-keepclassmembers enum * {
public static **[] values();
public static ** valueOf(java.lang.String);
}
-keep class * implements android.os.Parcelable {
public static final android.os.Parcelable$Creator *;
}</init></init></methods>
当在新版本的ADT创建项目时,混码的文件不再是proguard.cfg,而是project.properties和proguard-project.txt
如果需要对项目进行全局混码,只需要进行一步操作:
将project.properties的中 “#proguard.config=${sdk.dir}/tools/proguard/proguard-android.txt:proguard-project.txt”的“#”去掉就可以了。
proguard-project.txt示例
#工程中含有第三方jar包
-libraryjars libs/android-support-v4.jar
-libraryjars libs/BaiduLBS_Android.jar
#项目里面包含的包也不能混淆
-keep class com.baidu.** {*;}
-dontwarn com.baidu.**
-keep class vi.com.gdi.bgl.android.java.** {*;}
-dontwarn vi.com.gdi.bgl.android.java.**
-keep class android.** {*;}
-dontwarn android.**
其它代码混淆工具:
APKProtect,将流程代码也乱序混淆,对抗反编译工具、反ida动态调试、反模拟器、校验dex文件等功能。
一些问题处理:
Note: duplicate definition of library class [org.apache.http.conn.scheme.HostNameResolver]
Note: duplicate definition of library class [org.apache.http.conn.scheme.SocketFactory]
Note: duplicate definition of library class [org.apache.http.conn.ConnectTimeoutException]
Note: duplicate definition of library class [org.apache.http.params.HttpParams]
Note: duplicate definition of library class [android.net.http.SslCertificate$DName]
Note: duplicate definition of library class [android.net.http.SslError]
Note: duplicate definition of library class [android.net.http.SslCertificate]
在proguard-rules.pro添加
-printconfiguration config.txt
会看到生成的config.txt有:
-libraryjars 'D:\tools\android\platforms\android-23\android.jar'
-libraryjars 'D:\tools\android\platforms\android-23\optional\org.apache.http.legacy.jar'
那几个提示重复的class在 org.apache.http.legacy.jar和android.jar中重复定义。 目前处理方法只有使用:
-dontnote android.net.http.*
-dontnote org.apache.commons.codec.**
-dontnote org.apache.http.**