參考了許多大佬的部落格,在此特別誠摯感謝oacia大佬和其他大佬的部落格和指導!
flutter和apk基礎結構介紹
首先下載附件,是一個apk檔案,用jadx開啟
可以看見flutter字樣,而flutter是一種目前比較流行的android框架,很多app都是用的該框架構建,而該原生框架是建立在app的native層。
Android的系統架構採用了分層架構的思想。從下往上依次分為Linux核心、硬體抽象層(HAL)、系統Native庫和Android執行時環境、Java框架層以及應用層這5層架構,其中每一層都包含大量的子模組或子系統
而平時我們接觸到的都是應用層和Java框架層,包括用Jadx對apk進行逆向時也只是在逆向Java層的邏輯。如果想要逆向native層,就需要對android進行解包
apk本身是一個包,壓縮了執行時的依賴、配置檔案以及native庫,也就是.so,將apk檔案字尾名修改成.zip後,即可解壓檢視這些檔案
也可以使用androidkiller這個工具對apk進行分析、修改
最基礎的app配置檔案放在AndroidManifest.xml,這個檔案裡面存放的有app的很多配置,如該題的配置情況如下,可以在這個檔案裡面看到該應用的包名,名稱、SDK的版本等等資訊,這些資訊在app取證裡面很有用,對之後的動態除錯SO層也有很大幫助。
<?xml version="1.0" encoding="utf-8" standalone="no"?><manifest xmlns:android="http://schemas.android.com/apk/res/android" android:compileSdkVersion="33" android:compileSdkVersionCodename="13" package="com.example.flutter_application_1" platformBuildVersionCode="33" platformBuildVersionName="13">
<application android:appComponentFactory="androidx.core.app.CoreComponentFactory" android:icon="@mipmap/ic_launcher" android:label="flutter_application_1" android:name="android.app.Application">
<activity android:configChanges="density|fontScale|keyboard|keyboardHidden|layoutDirection|locale|orientation|screenLayout|screenSize|smallestScreenSize|uiMode" android:exported="true" android:hardwareAccelerated="true" android:launchMode="singleTop" android:name="com.example.flutter_application_1.MainActivity" android:theme="@style/LaunchTheme" android:windowSoftInputMode="adjustResize">
<meta-data android:name="io.flutter.embedding.android.NormalTheme" android:resource="@style/NormalTheme"/>
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER"/>
</intent-filter>
</activity>
<meta-data android:name="flutterEmbedding" android:value="2"/>
<uses-library android:name="androidx.window.extensions" android:required="false"/>
<uses-library android:name="androidx.window.sidecar" android:required="false"/>
</application>
</manifest>
至於其他的資料夾,大家可以自行查閱,這裡就不一一說明。
而native層的.so檔案就放在lib的幾個資料夾裡面
這三個資料夾分別代表了不同架構的.so檔案。我們如果想用真機除錯.so檔案,那麼就要用真機對應的架構,不能亂用。
blutter安裝以及使用
接下來把lib檔案進行解包,因為flutter使用的是dart語言,並且採用了dartVM的方法進行拍攝快照,所以我們現在要使用一些工具對.so檔案進行快照解析,市面上對flutter的逆向工具都是這個原理。
但是有一個問題,dart快照是可以更改的,隨著DartSdk版本的更新,reflutter和flutter逆向助手已經停止更新,這次的這個題flutterSDK過高,兩個工具都無法破解,於是找到了blutter這個工具
官方地址:
GitHub - worawit/blutter: Flutter Mobile Application Reverse Engineering Tool
用git把blutter.py拉進kali裡面(如果拉不進就直接到GitHub上下zip解壓就行),然後安裝依賴。
sudo apt install python3-pyelftools python3-requests git cmake ninja-build
build-essential pkg-config libicu-dev libcapstone-dev
若報錯如下
說明你該更新你的apt源了
sudo apt-get update
下載完成情況如圖
接下來就可以用這個工具了,將解壓後的app放進虛擬機器,在blutter目錄下執行.py檔案,注意有兩個引數,前一個引數是.so檔案所在的其中一個目錄,後一個引數是結果輸出目錄
若成功會解析稍微長一點的時間,耐心等待即可,如果有下圖結果即為解析完成
完成後在輸出目錄會有五個檔案和資料夾
按照作者的說法,分別對應的是
pp.txt:在物件池裡面的所有dart物件(dart採用了物件池的設計模式),這裡面可以檢視很多物件池變數的偏移地址
objs.txt:物件池中物件的完整(巢狀)轉儲,在這裡我理解成物件池裡面的方法和相應的偏移量
blutter_frida.js:這個是用於對該flutter程式hook的js程式碼,應用在frida這個工具裡面(接下來會講到)
ida_script:這個資料夾裝的是.so檔案的符號表還原指令碼,因為dart語言是依靠偏移量識別函式的,所以也能依靠偏移量還原函式
asm:對dart語言的反編譯結果,裡面有很多dart原始碼的對應偏移
動態除錯flutter程式
接下來就是利用frida工具hook插樁以及動態除錯破解該程式了
環境:具有python環境的win10系統、kali系統
裝置:pixel3(需要root)
重點:必須是歐版,如果不是歐版OEM無法開啟,不可能刷的了機
具體root過程參考https://sspai.com/post/76276
工具:adb除錯橋、IDA7.7工具
下載adb
https://blog.csdn.net/x2584179909/article/details/108319973
執行IDA
注意,在此之前需要將chall.apk修改成可除錯狀態
具體方法為利用androidkiller開啟程式->在AndroidManifest.xml裡面第二行插入
android:debuggable="true"
如果程式SDK版本比較老,這樣就可以,但是這個程式的targetSdkVersion是33,是高版本,簽名會出問題,所以在apktool.xml改成27或者28即可
兩處改好後就可以進行編譯,得到新的程式。
完成後即可安裝到手機上
adb install chall_killer.apk
檢視自己的手機是什麼架構可以用下列程式碼
adb shell getprop ro.product.cpu.abi
在ida的下圖資料夾內找到android_server64(我的真機架構是arm64位的)
連線手機(手機上開啟USB除錯),開啟終端,利用adb程式在手機上下載chall.apk,安裝完成後把之前找到的server檔案push到手機裡執行
adb push android_server64 /data/local/tmp/as
adb shell
su #載入手機root許可權
cd /data/local/tmp/
chmod 777 as #給server檔案可讀可寫可執行許可權
./as -p 12345 #用12345埠執行server
如果執行成功會有一個正在監聽的提示,說明這個命令端已經成為了server端監聽了
接下來重新開啟一個命令列,adb轉發埠
adb forward tcp:12345 tcp:12345
保持收發埠一致後啟動ida,將libapp.so放進ida
用剛才blutter解析得到的addName.py還原符號表
得到了符號表之後,檢視解析的asm裡面的main.dart,查詢主程式裡面的函式
在flutter官網查詢四個函式的含義均為dart的API
表單互動 (Forms)
或者可以在這篇部落格上找到
Flutter基建 - 按鈕全解析 - 掘金
onChanged():這個API在刪除或插入文字的時候的回撥函式
onSubmitted():當使用者完成文字輸入並按下鍵盤上的“完成”按鈕時的回撥函式
onLongPressed():在螢幕上保持了一段時間
onTap():使用者點選事件完成(點選提交按鈕時)
現在檢視我們的程式,可以看見這個程式的視窗組成,而最重要的應該是提交按鈕,對應的也就是onTap()回撥函式所做的
所以直接過濾器查詢這個函式(也可以直接用之前在main.dart裡面找到的函式地址)
回撥函式在0xE03C4處
之後我們檢視程式發現有256這個變數
再加上這裡很明顯的RC4加密流程
可以大概得知這是一個RC4加密。
frida工具hook key值
接下來需要用到frida工具,frida是一款基於python + java 的hook框架,可執行在android、ios、linux、win、osx等各平臺,主要使用動態二進位制插樁技術。
安裝部分可以看這裡
frida安裝正確流程
上面步驟中用blutter解析快照時,工具自動幫我們寫了一個插樁指令碼,叫做blutter_frida.js,只需要在下圖所示部分修改成上面有RC4加密的函式地址,即可hook出密文
改完之後使用frida載入這個js指令碼
frida -U -f com.example.flutter_application_1 -l blutter_frida.js
隨便輸入點什麼執行程式即可hook得到密文
動態除錯部分
現在可以除錯一下我們的apk應用程式
首先開啟應用debug模式,如果上面的androidkiller如果不行,可以用面具開,具體流程如下圖
adb shell
su
magisk resetprop ro.secure 0
magisk resetprop ro.debuggable 1
getprop ro.debuggable #如果回顯為1則已經開啟
stop
start #上面兩步重啟手機
這個時候下載monitor(DDMS)用於觀察程式程式是否開啟(如果是真機可能不需要這一步)
開啟monitor.bat,可以看見裝置上的程式
這個時候掛起程式
jdb -connect com.sun.jdi.SocketAttach:hostname=127.0.0.1,port=8639
執行結果如下圖
如果有報錯 致命錯誤:無法附加到目標 VM。
那可能是埠搞錯了,這裡要填寫的是應用程式的埠,而不是adb執行server的埠。
執行成功的話monitor裡面程式那行程式欄會顯示為綠色
接下來進行除錯,除錯設定如下圖
設定完成點選Attach to process...進行附加程式除錯,附加我們的程式即可
現在先找金鑰,而金鑰是RC4加密的異或操作下的變數,我們把斷點下在異或的指令上
f9斷到這個地方之後可以看見X2變數是有賦值的,我們利用trace跟蹤該變數,並將值都列印出來
import idc
print(idc.ger_reg_value('X2'),',',end='')
此處點選執行直接跳過,跳過後發現手機上能夠輸入了,這個時候輸入字元(字元個數可以往前看用frida工具hook出來的key數量)然後點√
感謝oacia師傅的提示,如果不點√就f9不會有輸入,程式會一直卡在第一個異或的金鑰上
上圖是第一個異或的金鑰,但是如果檢查下來發現密文和這個金鑰異或之後得不到輸入,重新檢查一下會發現還要異或一個0xff即可
addr = [14, 14, 68, 80, 29, 201, 241, 46, 197, 208, 123, 79, 187, 55, 234, 104, 40, 117, 133, 12, 67, 137, 91, 31, 136,
177, 64, 234, 24, 27, 26, 214, 122, 217]
key = [184,
132,
137,
215,
146,
65,
86,
157,
123,
100,
179,
131,
112,
170,
97,
210,
163,
179,
17,
171,
245,
30,
194,
144,
37,
41,
235,
121,
146,
210,
174,
92,
204,
22
]
flag = ""
for i in range(len(addr)):
flag += chr(addr[i] ^ 0xff ^ key[i])
print(flag)
4.本文知識點來源
[原創]flutter逆向 ACTF native app-Android安全-看雪-安全社群|安全招聘|kanxue.com
認識 Flutter 是什麼?
403 Forbidden
一日一技|如何 root 一臺 Pixel 手機 - 少數派
windows下載安裝adb(極其簡單)-CSDN部落格
frida安裝正確流程
Flutter基建 - 按鈕全解析 - 掘金
表單互動 (Forms)