Cycript高級技巧(轉載)

轉自 http://lsq.me/2014/01/12/cycript-tricks/ 自己留著看看的


引言

在分析iOS應用程序的時候,經常會用到Cycript這個工具。本文將介紹使用Cycript的一些基本命令和高級技巧。

打印Ivar值

很多時候輸入*varName就可以:

cy# *controller

{isa:"PrefsRootController",_contentView:">",_navBar:...

cy#

然而有時候卻不行:

cy# *UIApp

{message:"hasProperty callback returned true for a property that doesn't exist.",name:"ReferenceError"}

但是你可以這樣:

cy# [i for (i in *UIApp)]

["isa","_delegate","_touchMap","_exclusiveTouchWindows","_event",...

為了取得盡可能多的ivar值,你可以用下面這個函數:

function tryPrintIvars(a){ var x={}; for(i in *a){ try{ x[i] = (*a)[i]; } catch(e){} } return x; }

用法是:

cy# *a

{message:"hasProperty callback returned true for a property that doesn't exist.",name:"ReferenceError"}

cy# tryPrintIvars(a)

{isa:"SBWaveView",_layer:"",_tapInfo:null,_gestureInfo:null,_gestureRecognizers:...

打印方法名

可以取得方法名的函數:

function printMethods(className) {

var count = new new Type("I");

var methods =? ? ? class_copyMethodList(objc_getClass(className), count);

var methodsArray = [];

for(var i = 0; i < *count; i++) {

var method = methods[i];

methodsArray.push({selector:method_getName(method), implementation:method_getImplementation(method)});

}

free(methods);

free(count);

return methodsArray;

}

可以這樣用:

cy# printMethods("MailboxPrefsTableCell")

[{selector:@selector(layoutSubviews),implementation:0x302bf2e9},{selector:@selector(setCurrentMailbox:),implementation:0x302bee0d},...

cy#

你也可以只看isa的消息屬性,例如用UIApp.keyWindow.rootViewController.isa.messages可以取得rootViewControllers的方法。

用正則表達式取方法名

function methodsMatching(cls, regexp) { return [[new Selector(m).type(cls), m] for (m in cls.messages) if (!regexp || regexp.test(m))]; }

用法:

cy# methodsMatching(NSRunLoop, /forKey:$/)

[["v20@0:4I8@12@16","didChange:valuesAtIndexes:forKey:"],["v20@0:4I8@12@16","willChange:valuesAtIndexes:forKey:"],["v16@0:4@8@12","setValue:forKey:"]]

從地址獲取Objective-C對象

用new Instance(0xdeadbabe):

cy# var p = new Instance(0x8614390)

cy# p

[""]

載入框架

function loadFramework(fw) {

var h="/System/Library/",t="Frameworks/"+fw+".framework";

[[NSBundle bundleWithPath:h+t]||[NSBundle bundleWithPath:h+"Private"+t] load];

}

替換Objective-C方法

你可以通過替換messages數組的內容來模擬MSHookMessage:

cy# original_NSRunLoop_description = NSRunLoop.messages['description'];

0x339d94c3

cy# NSRunLoop.messages['description'] = function() { return original_NSRunLoop_description.call(this).toString().substr(0, 80)+", etc."; }

{}

cy# [NSRunLoop currentRunLoop]

"{locked = false, wait port = 0x1303, stopped = , etc."

注意func.call(this)的結構,就是它把原函數的this綁定到用戶指定的那個去了。如果需要更多地參數,用function(arg1, arg2, arg3, ...) {...func.call(self, arg1, arg2, arg3, ...);}來代替,例如:

cy# original_SpringBoard_menuButtonDown = SpringBoard.messages['menuButtonDown:']

0x17dbab1

cy# SpringBoard.messages['menuButtonDown:'] = function(arg1) {original_SpringBoard_menuButtonDown.call(this, arg1);}

function (e) {var e;var $cy0=this;original_SpringBoard_menuButtonDown.call($cy0,e);}

注意參數不會被自動映射到相對應的Objective-C類型,所以參數應該用[NSString stringWithString:"foo"]而不是簡單的"foo"。

獲取類方法

class.messages只包含實例方法。要hook類方法,你需要得到他的metaclass,一個簡單地方法是:

cy# NSRunLoop->isa.messages['currentRunLoop'] = ...

引入其他Cycript文件

從0.9.274-1開始,取消了導入native文件的組件。當Cycript需要hook到其他進程時,既然數據都保留在那兒,你可以首先加載那個.cy文件:

localhost:~ mobile$ cycript -p SpringBoard main.cy

0x12345678

localhost:~ mobile$ cycript -p SpringBoard

cy# ...

如果Cycript是獨立啟動的,使用Cycript編譯器和Javascript的eval表達式相結合也可以使引入作偽:

// include other .cy files

function include(fn) {

var t = [new NSTask init]; [t setLaunchPath:@"/usr/bin/cycript"]; [t setArguments:["-c", fn]];

var p = [NSPipe pipe]; [t setStandardOutput:p]; [t launch]; [t waitUntilExit];

var s = [new NSString initWithData:[[p fileHandleForReading] readDataToEndOfFile] encoding:4];

return this.eval(s.toString());

}

使用NSLog

在控制臺輸入:

NSLog_ = dlsym(RTLD_DEFAULT, "NSLog")

NSLog = function() { var types = 'v', args = [], count = arguments.length; for (var i = 0; i != count; ++i) { types += '@'; args.push(arguments[i]); } new Functor(NSLog_, types).apply(null, args); }

然后就可以像平常一樣使用NSLog:

cy# NSLog_ = dlsym(RTLD_DEFAULT, "NSLog")

0x31451329

cy# NSLog = function() { var types = 'v', args = [], count = arguments.length; for (var i = 0; i != count; ++i) { types += '@'; args.push(arguments[i]); } new Functor(NSLog_, types).apply(null, args); }

{}

cy# NSLog("w ivars: %@", tryPrintIvars(w))

如果已經attach到一個進程了,輸出就已經寫到syslog了:

Nov 17 20:26:01 iPhone3GS Foobar[551]: w ivars: {\n? ? contentView =

使用CGGeometry功能

為了使用CGGeometry類的函數,必須要在Cycript窗體輸入:

function CGPointMake(x, y) { return {x:x, y:y}; }

function CGSizeMake(w, h) { return {width:w, height:h}; }

function CGRectMake(x, y, w, h) { return? ? {origin:CGPointMake(x,y), size:CGSizeMake(w, h)}; }

將Cycript輸出寫入文件

Cycript的輸出時NSString,所以調用writeToFile然后把它保存起來時可能的,例如:

[[someObject someFunction] writeToFile:"/var/mobile/cycriptoutput.txt" atomically:NO encoding:4 error:NULL]

你可以這么用,下面是獲取SpringBoard view的結構的示例:

iPhone:~$ cycript -p SpringBoard

cy# [[UIApp->_uiController.window recursiveDescription] writeToFile:"/var/mobile/viewdump.txt" atomically:NO encoding:4 error:NULL]

打印View的繼承關系

iPhone:~$ cycript -p SpringBoard

cy# ?expand

expand == true

cy# UIApp.keyWindow.recursiveDescription

">

>

>

>

>

>

>

>

>

>

>

>

>

>

>

>"

?expand命令使換行顯示的更加正常,而不僅僅是\n。

參考文獻

Cycript Tricks

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市,隨后出現的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖,帶你破解...
    沈念sama閱讀 230,106評論 6 542
  • 序言:濱河連續發生了三起死亡事件,死亡現場離奇詭異,居然都是意外死亡,警方通過查閱死者的電腦和手機,發現死者居然都...
    沈念sama閱讀 99,441評論 3 429
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人,你說我怎么就攤上這事。” “怎么了?”我有些...
    開封第一講書人閱讀 178,211評論 0 383
  • 文/不壞的土叔 我叫張陵,是天一觀的道長。 經常有香客問我,道長,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 63,736評論 1 317
  • 正文 為了忘掉前任,我火速辦了婚禮,結果婚禮上,老公的妹妹穿的比我還像新娘。我一直安慰自己,他們只是感情好,可當我...
    茶點故事閱讀 72,475評論 6 412
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著,像睡著了一般。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發上,一...
    開封第一講書人閱讀 55,834評論 1 328
  • 那天,我揣著相機與錄音,去河邊找鬼。 笑死,一個胖子當著我的面吹牛,可吹牛的內容都是我干的。 我是一名探鬼主播,決...
    沈念sama閱讀 43,829評論 3 446
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 43,009評論 0 290
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后,有當地人在樹林里發現了一具尸體,經...
    沈念sama閱讀 49,559評論 1 335
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 41,306評論 3 358
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發現自己被綠了。 大學時的朋友給我發了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 43,516評論 1 374
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內的尸體忽然破棺而出,到底是詐尸還是另有隱情,我是刑警寧澤,帶...
    沈念sama閱讀 39,038評論 5 363
  • 正文 年R本政府宣布,位于F島的核電站,受9級特大地震影響,放射性物質發生泄漏。R本人自食惡果不足惜,卻給世界環境...
    茶點故事閱讀 44,728評論 3 348
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 35,132評論 0 28
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至,卻和暖如春,著一層夾襖步出監牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 36,443評論 1 295
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人。 一個月前我還...
    沈念sama閱讀 52,249評論 3 399
  • 正文 我出身青樓,卻偏偏與公主長得像,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 48,484評論 2 379

推薦閱讀更多精彩內容

  • 轉至元數據結尾創建: 董瀟偉,最新修改于: 十二月 23, 2016 轉至元數據起始第一章:isa和Class一....
    40c0490e5268閱讀 1,755評論 0 9
  • 工具 class-dump 用來提取已經砸過殼的 app 的頭文件 下載地址 http://stevenygard...
    輝g_9274閱讀 2,642評論 1 7
  • 單例模式 適用場景:可能會在場景中使用到對象,但只有一個實例,加載時并不主動創建,需要時才創建 最常見的單例模式,...
    Obeing閱讀 2,091評論 1 10
  • 今天去馬達單位咯 是驚喜的午餐約飯 然后愉快的下午電影時光 兩個人一起的值班 真是什么工作的干不了 喝咖啡 吃哈密...
    ninvxv閱讀 196評論 0 0
  • 我愛你 愿意變成一條狗 你總說你生活得像屎一樣 而狗也改不了吃屎 我愛你 愿意變成夸父 你做我的太陽 追你海角天邊...
    哥窯閱讀 436評論 0 5