標籤:try 欄位名 lda ali 工程 start lin stat pre
快速定位Android程式的關鍵代碼
1.通過apktool反編譯apk檔案,得到AndroidManifest.xml檔案,可以得到程式用到的組建、配置、以及主Activity
2.資訊反饋法(特殊字元串)
3.特徵函數法(Toast)
4.一行一行代碼看
5.插樁法
6.查看調用棧
7.Method Profiling(記錄每個函數的CPU時間,以及調用棧)
smali檔案格式
主要架構
.class <存取權限> [修飾關鍵字] <類名>
.super <父類名>
.source <原始碼名稱>
後面是具體的欄位、方法、註解(下面
欄位表示
靜態欄位:
#static fields.field <存取權限> static [修飾關鍵字] <欄位名>:<欄位類型>
執行個體欄位
#instance fields.field <存取權限> [修飾關鍵字] <欄位名>:<欄位類型>
方法表示
.method <存取權限> [修飾關鍵字] <方法原型>.prologue具體代碼.end method
介面
.implements <介面名>
註解類
.annotation [註解屬性] <註解類名> [註解欄位 = 值].end annotation
Android程式中的類
baksmali反編譯dex檔案時,會為每一個類都產生一個smali檔案
內部類
如下
class Outer{ class Inner{}}
baksmali反編譯的時候會產生 Outer.smali檔案 與 Outer$Inner.smali檔案。其中內部內檔案名稱形式為"[外部類]$[內部類].smali"。
我們開啟Outer$Inner.smali檔案會發現,存在一個this$0 的synthetic的欄位(synthetic表示由編譯器合成),其指向父類,供內部類的其他方法調用(其中0表示第幾層父類)
查看內部類的初始化函數,我們可以發現該類的初始化為:先儲存外部類的引用,然後調用父類的建構函式,然後是自身的初始化
監聽器
也就是匿名類,其形式與內部類差不多。檔案名稱形式為"[外部類]$[數字].smali"
註解類
#annotations.annotation system Ldalvik/annotation/Memberclasses; value = { Lcom/droider/crackme/MainActivity#SNChecker; }.end annotation
MemberClasses為父類提供一個member classes 列表.通俗的將就是一個內部類列表
#annotations.annotation system Ldalvik/annotation/EnclosingMethod; value = { Lcom/droider/crackme/MainActivity;->onCreate()V; }.end annotation
EnclosingMehtod註解用來說明其作用範圍,Method表示他作用於一個方法。value表示其作用的具體類中的函數.相應的還用EnclosingClass註解
#annotations.annotation system Ldalvik/annotation/InnerClass; accessFlags = 0x1 name = "SNChecker".end annotation
InnerClass註解表示類為一個內部類
自動產生的類R類
每個工程下的res目錄下的每個資源都會有一個id,其儲存在R類中
閱讀反組譯碼的smali代碼迴圈語句
- 迭代器(hasNext,next)
- 普通迴圈(x86反組譯碼形式差不多)
switch 分支語句
- packed-switch(有規律的)
- sparse-switch (無規律的)
smali格式大概如下:
xxxxx-switch p0,switch_goto_table
switch_goto_table指向一個跳轉表。
其中預設 default 分支 位於 xxxxx-switch p0,switch_goto_table 指令之後
try-catch 語句
smali 代碼中,try語句塊使用 try_start_x ,try_end_x 包圍 (其中 x為數字).
在 try_end_x下面是.catch 指令,指定處理的異常類型與處理代碼的位置
在處理catch代碼時,發現異常會調用外圍catch
靜態分析Android程式