教你如何動(dòng)態(tài)調(diào)試 iOS App(反編譯App)

教你如何動(dòng)態(tài)調(diào)試?iOS App(反編譯App)開(kāi)篇

通過(guò)本文你能了解?iOS?逆向的基本知識(shí),對(duì)?iOS App?的安全有一定了解。然后能舉一反三,在?自家?App?找到危險(xiǎn)漏洞加以預(yù)防,保證?戶數(shù)據(jù)安全。?

在安全領(lǐng)域,攻與防永遠(yuǎn)存在。哪怕是?iPhone?有著強(qiáng)大的安全防護(hù)機(jī)制,也擋不住那些極客們一次?一次的好奇,開(kāi)發(fā)了很多強(qiáng)?且便利的?工具。本文就是在這些極客們提供的工具的基礎(chǔ)上完成的!

準(zhǔn)備工具

Mac?電腦和越獄?iPhone??機(jī)?

查看手機(jī)系統(tǒng)目錄工具: iFunbox?或?iTools

網(wǎng)絡(luò)分析工具:Charles

反編譯?具:Hopper,?IDA Pro

查看頭文件工具:class-dump

砸殼工具:dumpdecrypted,?Clutch

調(diào)試器器:lldb?或?gdb

調(diào)試工具:Cycript

HTTP(S)?抓包

HTTP?抓包

第一步:獲取?MAC IP

按下Option鍵,同時(shí)點(diǎn)擊?Mac?菜單欄上的?無(wú)線?網(wǎng)?Icon,能看到當(dāng)前電腦的?IP?地址。 或在終端輸入?ifconfig en0?也可查看。

第?步:設(shè)置代理

保證?機(jī)和電腦在同一?WIFI?下,在手機(jī)上,點(diǎn)擊“設(shè)置->?無(wú)線局域?網(wǎng)->連接的WiFi”,設(shè)置HTTP代理理:?

服務(wù)器器:為?Mac?電腦?IP?地址(如192.168.1.122)

端口:8888

第三步:抓包

在電腦端,打開(kāi)?Charles。使?機(jī)發(fā)?生?網(wǎng)絡(luò)請(qǐng)求,Charles?會(huì)彈出一個(gè)詢問(wèn)的對(duì)話框

點(diǎn)擊“Allow”允許,Charles?會(huì)出現(xiàn)手機(jī)的?HTTP?請(qǐng)求記錄列表。

HTTPS?抓包

第一步: 獲取證書(shū)安裝地址

安裝?SSL?證書(shū)到?機(jī)設(shè)備。點(diǎn)擊?Help -> SSL Proxying -> Install Charles Root Certificate on a Mobile Device

出現(xiàn)彈窗得到地址?chls.pro/ssl

第二步:iPhone?安裝證書(shū)

在?機(jī)?Safari?瀏覽器輸?地址?chls.pro/ssl,出現(xiàn)證書(shū)安裝頁(yè)面,點(diǎn)擊安裝,?機(jī)設(shè)置有密碼的輸入密碼進(jìn)行安裝

第三步:配置代理理?host

Charles?設(shè)置?Proxy。選擇?Proxy -> SSL Proxying Settings...

勾選?Enable SSL Proxying,點(diǎn)擊?Add

Host?設(shè)置要抓取的?HTTPS?接?,Port?填寫(xiě)?443。

讓手機(jī)重新發(fā)送?

HTTPS?請(qǐng)求,可看到抓包。

注意:不抓包請(qǐng)關(guān)閉手機(jī)?HTTP?代理理,否則斷開(kāi)與電腦連接后會(huì)連不上網(wǎng)!

拿到?.h?頭文件

從?AppStore?直接下載的?ipa, 蘋(píng)果公司對(duì)其做了 FairPlay DRM?技術(shù)進(jìn)?行行加密保護(hù),?法直接使? class-dump 工具獲取頭文件。但是如果是通過(guò)?development?打包出來(lái)的話的?App 的話,是可以直接使用?class-dump?查看所有頭?件的,此部分介紹就是通過(guò)此情況來(lái)說(shuō)明如何獲取?.h??件的。 此處不再介紹?class-dump 工具的安裝過(guò)程,具體步驟請(qǐng)直接百度。

進(jìn)?到 appName.ipa?所在?錄,修改擴(kuò)展名為?.zip,然后解壓文件,得到?appName.app。

然后執(zhí)行:

class-dump -H appName.app -o ./headers/

命令執(zhí)行完成后,會(huì)在當(dāng)前?錄下的?headers 目錄?里里看到?app?所有頭?件。 如果添加參數(shù)?-A -S?會(huì)在頭文件?里里標(biāo)記處類?法和屬性的?IMP?地址(模塊偏移前基地址)。

class-dump -H -A -S appName.app -o ./headers/

SSH?訪問(wèn)手機(jī)?件?錄

在你的越獄手機(jī)上使用?Cydia?應(yīng)用市場(chǎng)安裝?OpenSSH,并保證?Mac?和?iPhone?處于同?個(gè)WIFI下,在?MAC?終端輸入:ssh root@IP?,IP?替換為?iPhone?的?IP?地址

輸?默認(rèn)密碼:alpine即可進(jìn)? iPhone?終端。

使用?Clutch?反編譯?App

第一步:重新簽名?debugserver

取得?debugserver?有兩種?式。

第一種是在?Mac?電腦中拿到

進(jìn)入路路徑?/Applications/Xcode.app/Contents/Developer/Platforms/iPhoneOS.platform/DeviceSupport/8.3/DeveloperDiskImage.dmg?(其中路路徑?里里8.3,代表?iOS?系統(tǒng)版本,需與準(zhǔn)備的越獄?機(jī)系統(tǒng)版本保持一致)。雙擊?DeveloperDiskImage.dmg,將目錄里的?usr/bin/debugserver?復(fù)制到指定文件夾中。

第二種是在越獄手機(jī)里拿到

如果手機(jī)連接過(guò)手機(jī)并通過(guò)?XCode?調(diào)試過(guò)?app,會(huì)在?機(jī)?里里的?/Developer/usr/bin/ 目錄下?生成一個(gè)?debugserver 文件。通過(guò)?iFunbox?導(dǎo)出?至?Mac?桌面。或使? scp?命令?cpoy?出 來(lái)。

第二步:重簽名?debugserver

即給?debugserver?添加?task_for_pid?權(quán)限 創(chuàng)建?entitlements.plist,添加如下四個(gè)?key:

com.apple.springboard.debugapplications?

get-task-allow

task_for_pid-allow

run-unsigned-code

key?對(duì)應(yīng)的?value?都設(shè)為設(shè)為?ture

將?entitlements.plist?和?debugserver?放在同?個(gè)目錄下,執(zhí)?行行以下命令:

codesign -s - --entitlements entitlements.plist -f debugserver

此命令會(huì)重新簽名?debugserver,將簽名后的?debugserver?拷??手機(jī)系統(tǒng)的?/usr/bin/ 目錄下。注意:不要將?debugserver?拷貝至?/Developer/usr/bin/?路徑下

第三步: 通過(guò)?Clutch?拿到反編譯后的?App?可執(zhí)行文件

將下載好的?Clutch?放?手機(jī)的?/usr/bin/?路徑下。然后,給?Clutch?賦予權(quán)限,通過(guò)?SSH?登錄到手機(jī),進(jìn)? /usr/bin/?執(zhí)行?chmod a+x ./Clutch?。 通過(guò)命令?Clutch -i?,列出所有的可被?Clutch?的應(yīng)用。

對(duì)指定序號(hào)的應(yīng)用進(jìn)行脫殼,如企業(yè)微信,序號(hào)是1,命令是?Clutch -d 1?。執(zhí)行完成后,會(huì)得到脫殼后的?ipa。

第四步:使用?class-dump?拿到?.h?頭文件

使用上文?【拿到.h頭?件】?介紹的方法拿到脫殼后的?App?頭文件和并記下要打斷點(diǎn)的方法的?IMP?地址。

動(dòng)態(tài)調(diào)試?App

本?動(dòng)態(tài)調(diào)試?到的調(diào)試器器是?lldb。

第?步:使?iPhone?進(jìn)?等待掛載狀態(tài)

SSH?登錄到手機(jī),執(zhí)行?ps -e?命令得到?App PID?或項(xiàng)目名稱。

進(jìn)入?/usr/bin/?執(zhí)行?./debugserver IP:port -a PID|appProjectName?。 其中第一個(gè)參數(shù)?IP?可以替換為?Mac?電腦?IP地址,或者使用?*?通配符,允許所有?IP?調(diào)試;第二個(gè) 參數(shù)?port?隨便寫(xiě)一個(gè)就行。第四個(gè)參數(shù) 可以指定要調(diào)試?App?的?PID?或項(xiàng)目名稱。?如要調(diào)試的?PID?為?6019?的搜狗輸?法項(xiàng)目名稱為SogouInput,則命令即為:

./debugserver *:1234 -a 6019?或?./debugserver *:1234 -a ‘SogouInput’

此命令執(zhí)行完成后,app會(huì)進(jìn)?等到掛載狀態(tài),app會(huì)被卡住點(diǎn)擊無(wú)反應(yīng)。正常現(xiàn)象!

如果此命令報(bào)錯(cuò),如出現(xiàn)?Segmentation fault: 11?等情況,說(shuō)明?App?做了反動(dòng)態(tài)調(diào)試保護(hù)。遇到此種情況,需先確定?App?采?了哪種保護(hù)?案,然后進(jìn)一步找到對(duì)應(yīng)措施,干掉它的反動(dòng)態(tài)調(diào)試保護(hù)。

第二步:監(jiān)聽(tīng)進(jìn)程,進(jìn)?掛載狀態(tài)

重新打開(kāi)一個(gè)?Mac?終端執(zhí)行?lldb?進(jìn)入?lldb?調(diào)試狀態(tài)。然后輸?

process connect connect://iPhoneIP:port

iPhoneIP?替換為?iPhone?的?IP?地址;port?改為剛才指定的端口,即?1234。 待命令執(zhí)行完成后,App?即進(jìn)?掛載狀態(tài)。

第三步:獲取?App?的?ASLR?偏??移量

ASLR偏移量其實(shí)就是虛擬內(nèi)存的地址相對(duì)于模塊基地址的偏移量。有兩個(gè)概念需要熟悉一下:

模塊在內(nèi)存中的起始地址?----?模塊基地址

ASLR偏移?----?虛擬內(nèi)存起始地址與模塊基地址的偏移量

在?lldb?調(diào)試器器模式下,執(zhí)?行行?imge list -o -f

模塊偏移后的基地址?= ASLR?偏移量?+?模塊偏移前基地址(?法的?IMP?地址)

上?面這個(gè)公式是尤為重要的,因?yàn)?Class-dump?中顯示的都是“模塊偏移前基地址”,?而?lldb?要操作的都是“模塊偏移后的基地址”。所以從?Class-dump?到?lldb?要做一個(gè)地址偏移量的轉(zhuǎn)換。

?此,已得到了App?的?ASLR?偏移量和?法的?IMP?地址。

第四步:打斷點(diǎn),調(diào)試

在?lldb?模式下執(zhí)?行行,?br s -a 'ASLR?偏移量+ IMP'?,然后執(zhí)?行行?c?,使?App?跑起來(lái),觸發(fā)一個(gè)?法調(diào)用,就會(huì)進(jìn)入斷點(diǎn)模式。輸入?po $arg1?打印第?個(gè)參數(shù)。 然后,配合著抓包工具?Charles(?比如分析網(wǎng)絡(luò)請(qǐng)求加密邏輯)?和?Class-dump(?比如修改某個(gè)類的方法返回值)等?具,你就可以隨意動(dòng)態(tài)調(diào)試?App 了,就像在?XCode??里里調(diào)試一樣!

?br?命令說(shuō)明

br dis 1 --?禁?(disable)編號(hào)為1的斷點(diǎn)

?br en 1 --?啟用(enable)編號(hào)為1的斷點(diǎn)

?br dis --?禁用所有斷點(diǎn)

br en --?啟用所有斷點(diǎn)

br del 1 --?刪除(delete)編號(hào)為1的斷點(diǎn)?

br del --?刪除所有斷點(diǎn)

br list -- 列出所有斷點(diǎn)

使用?dumpdecrypted?破殼?App

dumpdecrypted?脫殼工具的原理理是:將應(yīng)用程序運(yùn)行起來(lái)(iOS?系統(tǒng)會(huì)先解密程序再啟動(dòng)),然后將內(nèi)存中的解密結(jié)果?dump?寫(xiě)?入文件中,得到一個(gè)新的可執(zhí)行程序。

第一步:?生成?.dylib 文件

在終端進(jìn)?到下載后的目錄中,?cd dumpdecrypted-master?,然后執(zhí)行?make?,即可生成?dumpdecrypted.dylib

第?步:找到?App?的?Documents 文件夾路路徑

通過(guò)?SSH?登錄到?iPhone,然后執(zhí)行?ps -e?查看進(jìn)程,獲取要破殼的進(jìn)程?PID。然后執(zhí)行?cycript -p PID?附加到?PID?進(jìn)程上。最后執(zhí)

[[NSFileManager defaultManager] URLsForDirectory:NSDocumentDirectory inDomains:NSUserDomainMask][0]?得到?Documents 文件夾路路徑。

?第三步:開(kāi)始破殼

將第一步生成的?dumpdecrypted.dylib?拷?貝到第二步得到的?.../Documents/?路路徑下,命令如下:

scp ~/dumpdecrypted.dylib root@IP:/var/mobile/Containers/Data/Application/2B4C6281-C015-4FF3-A8EC-5E5C7554D447/Documents?(將路徑?里里的UDID?替換為你的要破殼的?App?的?UDID)

進(jìn)?入?Documents 目錄下,執(zhí)?

?DYLD_INSERT_LIBRARIES=dumpdecrypted.dylib /var/mobile/Containers/Bundle/ Application/BFED82A3-3238-4F41-B797-C1CB584CBE05/appProjectNa (路徑里的?UDID?替換為你的要破殼的?App?的?UDID;將?appProjectName?替換為要破殼?App?的項(xiàng)?名稱)

待命令執(zhí)行完,會(huì)在當(dāng)前目錄?生成?一個(gè)名為?appProject.decrypted?的文件,這個(gè)就是破殼后的?App?可執(zhí)?文件,要的就是它!使用?Class-dump?即可得到頭文件。或使? Hopper?或?IDA Pro?進(jìn)?反編譯。

給你的?App?添加反動(dòng)態(tài)調(diào)試機(jī)制

?ptrace

為了?便便應(yīng)用軟件的開(kāi)發(fā)和調(diào)試,從Unix的早期版本開(kāi)始就提供了一種對(duì)運(yùn)行中的進(jìn)程進(jìn)行跟蹤和控制的手段,那就是系統(tǒng)調(diào)用?ptrace()。 通過(guò)?ptrace?可以對(duì)另?個(gè)進(jìn)程實(shí)現(xiàn)調(diào)試跟 蹤,同時(shí)?ptrace?還提供了一個(gè)?常有?的參數(shù)那就是?PTDENYATTACH,這個(gè)參數(shù)用來(lái)告訴系統(tǒng),阻止調(diào)試器器依附。

所以最常用的反調(diào)試方案就是通過(guò)調(diào)用ptrace來(lái)實(shí)現(xiàn)反調(diào)試。?

sysctl

當(dāng)?個(gè)進(jìn)程被調(diào)試的時(shí)候,該進(jìn)程會(huì)有一個(gè)標(biāo)記來(lái)標(biāo)記?己正在被調(diào)試,所以可以通過(guò)?sysctl?去查看當(dāng)前進(jìn)程的信息,看有沒(méi)有這個(gè)標(biāo)記位即可檢查當(dāng)前調(diào)試狀態(tài)。 檢測(cè)到調(diào)試器就退出,或者制造崩潰,或者隱藏工程,當(dāng)然也可以定時(shí)去查看有沒(méi)有這個(gè)標(biāo)記。

syscall

為從實(shí)現(xiàn)從用戶態(tài)切換到內(nèi)核態(tài),系統(tǒng)提供了一個(gè)系統(tǒng)調(diào)?函數(shù)?syscall,上?面講到的?ptrace?也是通過(guò)系統(tǒng)調(diào)用去實(shí)現(xiàn)的。 在Kernel Syscalls27 這?里里可以找到?ptrace?對(duì)應(yīng)的編號(hào)。

26. ptrace 801e812c T

所以如下的調(diào)?等同于調(diào)用?ptrace:syscall(26,31,0,0,0);

arm

syscall?是通過(guò)軟中斷來(lái)實(shí)現(xiàn)從用戶態(tài)到內(nèi)核態(tài),也可以通過(guò)匯編?svc?調(diào)用來(lái)實(shí)現(xiàn)。?

覺(jué)得不錯(cuò)的話,歡迎關(guān)注我的公眾號(hào)哦!



最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書(shū)系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

推薦閱讀更多精彩內(nèi)容

  • 前言 本文是自己對(duì)iOS逆向工程領(lǐng)域所學(xué)的一個(gè)總結(jié),文中所用的例子僅為學(xué)習(xí)研究使用。 1. 逆向工程是什么? 從i...
    JimmyCJJ閱讀 5,669評(píng)論 3 15
  • 教你如何反編譯app,拿到加密方式 大家知道app 有安卓和ios 安卓是apk 現(xiàn)在基本上apk都是經(jīng)過(guò)加密的 ...
    叫我老村長(zhǎng)閱讀 3,631評(píng)論 0 10
  • layout: wikititle: iOS逆向分析筆記categories: Reverse_Engineeri...
    超哥__閱讀 10,921評(píng)論 3 16
  • 應(yīng)用場(chǎng)景 在了解iOS逆向工程之前,我們有必要了解它究竟能做什么,在開(kāi)發(fā)中能夠獲得哪些幫助?個(gè)人覺(jué)得有以下四點(diǎn) 促...
    郡王丶千夜閱讀 682評(píng)論 0 1
  • 為了表示我對(duì)簡(jiǎn)書(shū)『飽醉豚』事件的不滿,簡(jiǎn)書(shū)不再更新,后續(xù)有文章只更新 個(gè)人博客和 掘金 歡迎移步 個(gè)人博客或者 掘...
    eagleyz閱讀 7,270評(píng)論 0 4