【问题标题】:Android, what Proguard exactly does?Android,Proguard 到底是做什么的?
【发布时间】:2012-12-05 08:37:47
【问题描述】:

我正在使用 Proguard 来混淆我的代码。所以,我在project.propertise 文件中激活它。

之后我通过apktool反编译了APK文件。

反编译后的文件有res、smali、AndroidManifest三个项目。 在 res 文件夹中,我可以清楚地看到我的图像 :) 在 smali 中,这并不容易理解,但我仍然可以找到我的代码。是这样的:

.method public static u()Ljava/lang/String;
    .locals 1

    const/4 v0, 0x1

    packed-switch v0, :pswitch_data_0

    const-string v0, "https://uat.somewhere.com/ebroking/wecos/mobiletrader/aboutus.html"

    :goto_0
    return-object v0

    :pswitch_0
    const-string v0, "https://www2.somewhere.com/ebroking/wecos/mobiletrader/aboutus.html"

    goto :goto_0

    :pswitch_data_0
    .packed-switch 0x1
        :pswitch_0
    .end packed-switch

如果我转到包名称(活动),有几个文件,如 a.smali、aa.smali、ab.smali、ac.smali 等。此外,在这个文件夹中我可以看到我的所有活动。例如,在我的应用程序中,我有一个名为 MSAboutUs 的活动。在 smali 文件夹中,它的名称是 MSAboutUs.smali。当我打开它时,我可以看到以下代码:

    .class public Lcom/pbb/mystock/activities/MSAboutUs;
.super Lcom/pbb/mystock/activities/ay;


# instance fields
.field private j:Landroid/widget/Button;

.field private k:Landroid/webkit/WebView;


# direct methods
.method public constructor <init>()V
    .locals 0

    invoke-direct {p0}, Lcom/pbb/mystock/activities/ay;-><init>()V

    return-void
.end method


# virtual methods
.method public onCreate(Landroid/os/Bundle;)V
    .locals 3

    invoke-super {p0, p1}, Lcom/pbb/mystock/activities/ay;->onCreate(Landroid/os/Bundle;)V

    const v0, 0x7f030004

    invoke-virtual {p0, v0}, Lcom/pbb/mystock/activities/MSAboutUs;->setContentView(I)V

    const-string v0, ""

    const-string v1, "Loading..."

    const/4 v2, 0x1

    invoke-static {p0, v0, v1, v2}, Landroid/app/ProgressDialog;->show(Landroid/content/Context;Ljava/lang/CharSequence;Ljava/lang/CharSequence;Z)Landroid/app/ProgressDialog;

    move-result-object v0

    iput-object v0, p0, Lcom/pbb/mystock/activities/MSAboutUs;->a:Landroid/app/ProgressDialog;

    const v0, 0x7f060008

    invoke-virtual {p0, v0}, Lcom/pbb/mystock/activities/MSAboutUs;->findViewById(I)Landroid/view/View;

    move-result-object v0

    check-cast v0, Landroid/webkit/WebView;

    iput-object v0, p0, Lcom/pbb/mystock/activities/MSAboutUs;->k:Landroid/webkit/WebView;

    iget-object v0, p0, Lcom/pbb/mystock/activities/MSAboutUs;->k:Landroid/webkit/WebView;

    new-instance v1, Lcom/pbb/mystock/activities/a;

    invoke-direct {v1, p0}, Lcom/pbb/mystock/activities/a;-><init>(Lcom/pbb/mystock/activities/MSAboutUs;)V

    invoke-virtual {v0, v1}, Landroid/webkit/WebView;->setWebViewClient(Landroid/webkit/WebViewClient;)V

    iget-object v0, p0, Lcom/pbb/mystock/activities/MSAboutUs;->k:Landroid/webkit/WebView;

    invoke-static {}, Lcom/pbb/mystock/a/b;->u()Ljava/lang/String;

    move-result-object v1

    invoke-virtual {v0, v1}, Landroid/webkit/WebView;->loadUrl(Ljava/lang/String;)V

    const v0, 0x7f060007

    invoke-virtual {p0, v0}, Lcom/pbb/mystock/activities/MSAboutUs;->findViewById(I)Landroid/view/View;

    move-result-object v0

    check-cast v0, Landroid/widget/Button;

    iput-object v0, p0, Lcom/pbb/mystock/activities/MSAboutUs;->j:Landroid/widget/Button;

    iget-object v0, p0, Lcom/pbb/mystock/activities/MSAboutUs;->j:Landroid/widget/Button;

    new-instance v1, Lcom/pbb/mystock/activities/b;

    invoke-direct {v1, p0}, Lcom/pbb/mystock/activities/b;-><init>(Lcom/pbb/mystock/activities/MSAboutUs;)V

    invoke-virtual {v0, v1}, Landroid/widget/Button;->setOnClickListener(Landroid/view/View$OnClickListener;)V

    const v0, 0x7f060009

    invoke-virtual {p0, v0}, Lcom/pbb/mystock/activities/MSAboutUs;->findViewById(I)Landroid/view/View;

    move-result-object v0

    check-cast v0, Landroid/widget/Button;

    const v1, 0x7f06000a

    invoke-virtual {p0, v1}, Lcom/pbb/mystock/activities/MSAboutUs;->findViewById(I)Landroid/view/View;

    move-result-object v1

    check-cast v1, Landroid/widget/HorizontalScrollView;

    invoke-virtual {p0, v0, v1}, Lcom/pbb/mystock/activities/MSAboutUs;->a(Landroid/widget/Button;Landroid/widget/HorizontalScrollView;)V

    invoke-virtual {p0}, Lcom/pbb/mystock/activities/MSAboutUs;->d()V

    return-void
.end method

.method public onKeyDown(ILandroid/view/KeyEvent;)Z
    .locals 1

    const/4 v0, 0x4

    if-ne p1, v0, :cond_0

    const/high16 v0, 0x7f04

    invoke-virtual {p0, v0}, Lcom/pbb/mystock/activities/MSAboutUs;->getString(I)Ljava/lang/String;

    move-result-object v0

    invoke-virtual {p0, v0}, Lcom/pbb/mystock/activities/MSAboutUs;->b(Ljava/lang/String;)V

    :cond_0
    const/4 v0, 0x0

    return v0
.end method

这与其他活动相同。我可以看到登录活动 EditTexts 和按钮。我敢肯定,花一些时间来了解什么是架构然后操作代码是可能的。

所以我的问题是 Progaurd 到底在做什么?我以为它会更改类、方法和变量的名称,但似乎没有任何改变。

在应用程序的prject.properties 中,我添加了这一行:

proguard.config=proguard.cfg

proguard.cfg 包括以下几行:

# This is a configuration file for ProGuard.
# http://proguard.sourceforge.net/index.html#manual/usage.html

-dontusemixedcaseclassnames
-dontskipnonpubliclibraryclasses
-verbose

# Optimization is turned off by default. Dex does not like code run
# through the ProGuard optimize and preverify steps (and performs some
# of these optimizations on its own).
-dontoptimize
-dontpreverify
# Note that if you want to enable optimization, you cannot just
# include optimization flags in your own project configuration file;
# instead you will need to point to the
# "proguard-android-optimize.txt" file instead of this one from your
# project.properties file.

-keepattributes *Annotation*
-keep public class com.google.vending.licensing.ILicensingService
-keep public class com.android.vending.licensing.ILicensingService

# For native methods, see http://proguard.sourceforge.net/manual/examples.html#native
-keepclasseswithmembernames class * {
    native <methods>;
}

# keep setters in Views so that animations can still work.
# see http://proguard.sourceforge.net/manual/examples.html#beans
-keepclassmembers public class * extends android.view.View {
   void set*(***);
   *** get*();
}

# We want to keep methods in Activity that could be used in the XML attribute onClick
-keepclassmembers class * extends android.app.Activity {
   public void *(android.view.View);
}

# For enumeration classes, see http://proguard.sourceforge.net/manual/examples.html#enumerations
-keepclassmembers enum * {
    public static **[] values();
    public static ** valueOf(java.lang.String);
}

-keep class * implements android.os.Parcelable {
  public static final android.os.Parcelable$Creator *;
}

-keepclassmembers class **.R$* {
    public static <fields>;
}

# The support library contains references to newer platform versions.
# Don't warn about those in case this app is linking against an older
# platform version.  We know about them, and they are safe.
-dontwarn android.support.**

# Remove all logs
-assumenosideeffects class android.util.Log {
    public static *** v(...);
    public static *** d(...);
    public static *** i(...);
    public static *** w(...);
    public static *** e(...);
}

-keepattributes JavascriptInterface
-keep public class com.pbb.mystock.activities.MSLogin2$MyJavaScriptInterface
-keep public class * implements com.pbb.mystock.activities.MSLogin2$JavaScriptInterface
-keepclassmembers class com.pbb.mystock.activities.MSLogin2$JavaScriptInterface { 
    void processHTML(***); 
}

【问题讨论】:

  • 你的标题问“...... Proguard 到底是做什么的?”在您的问题中,您声明“我正在使用 Proguard 来混淆我的代码。”。 - 尽管我怀疑您不了解混淆的含义,但您基本上已经回答了自己的问题。混淆意味着“隐藏”或“混淆”。换句话说,Proguard 只是让直接解释 apk 中的代码变得不那么容易。这并不意味着它会对其进行加密或使其 100% 安全。
  • 谢谢 Squonk,是的,你是对的,但我希望当我隐藏或混淆某些东西时,我又看不清楚了。这就是为什么我问它是做什么的。如果它令人困惑,那么我不应该清楚地看到我的班级名称。那么,它在做什么???也许尼古拉的回答是对的。

标签: android proguard


【解决方案1】:

它的作用与在其他平台上的作用相同,有关详细信息,请参阅FAQ。在 Andorid 上,您必须保留清单中定义的活动、服务和其他组件的名称,因为操作系统按名称引用它们。 onCreate() 等生命周期方法也是如此。资源不会以任何方式修改。非组件类 (POJO) 将被重命名,它们的方法和字段也将被重命名。它最终取决于您使用的配置文件的内容。

正如您所注意到的,这并不能完美地隐藏您的代码,什么都没有。它只是让反编译时更难阅读。你可以试试DexGuard,它做得更多,但最终如果有人足够坚定,他们可以反转你的代码(本机代码也是如此)

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2015-08-06
    • 2013-09-02
    • 2014-01-02
    • 2013-10-10
    • 2017-05-08
    • 2022-01-20
    • 2012-10-17
    相关资源
    最近更新 更多