IDA Proを使い始めた

およそ2ヶ月前くらいにIDA Proのメジャーアップデートが行われ,7.0がリリースされた.約一年ぶりのアップデートとなったが,もっとも大きな変更点はついにIDA Proそのものが64bitアプリケーションになったことである.かねてより購入機会を伺っていた僕は,これを機にMac版のNamed Licenseを購入することにした.

IDA Pro Named License購入チャレンジ

ところがquotation systemを見ればわかる通り,現在IDA Pro Named Licenseは全てのプラットフォームにおいて販売されていない.詳しいことは不明だが,知り合い曰くバージョン7.0がリリースされた直後に本体およびデコンパイラのライセンスがリークされ,それを受けての対応ではないかとのこと.
当初Google CTFのfinalsが直前に迫っており,せっかくならここに間に合わせたいということで急遽メールで交渉することにした.

欲しいライセンスは IDA Pro Named License [Mac] なんだけど,
なんか今全部のNamed Licenseが買えないみたいなんですよ.
新しくNamed License売ってくれない?w

みたいなことを書いて sales[at]hex-rays.com にメールを送った. すると半日くらいで返信が来て,

会社のメールアドレスから送ってくれや.

僕はまだ学生なわけで当然会社のメールアドレスは持っていない.とりあえず大学のメールアドレスを使って再度送信.

OKわかった.欲しいライセンスはお前に紐付く個人ライセンスでいいんだな?
quoteは用意できる.請求先住所を教えてくれ.

とまあ意外とすんなり通った.
あとはメールアドレスを変えたい旨を伝えたら最初のメールアドレスで手続きしてもらえたので,そのまま普段のメールアドレスをライセンスに紐づけることができた.

とにかくHex-Raysの人の対応が早くて,営業時間内なら1,2時間程度で返事が返ってきた.おかげで東京を出発する日にメール手続きを始めたにも関わらずフランスでのトランジット中にダウンロードリンクが降ってきて,そのまま空港の回線を使ってIDAを雑にインストールするといったことをしてた (回線を圧迫したけど深夜だったし許して) . 実はクレカの限度額が足りなくて急遽デビッドカードに切り替えたり,3Dセキュアに対応してないカードはrejectされるため羽田空港の搭乗口で3Dセキュアを有効化したりドタバタしていたんだけどそれはまた別の話.

エクストリームIDA購入チャレンジめいたものに見事勝利したわけだが,結局Google CTFでは使わなかった.

macOSでIDA Pythonをいい感じに使いたい

話は変わって,現実逃避をするために最近少し余裕が出て来たのでIDA Pluginをいくつか試してみることにした. まず最初に試そうと思ったのはPonceだったがこれはまだ7.0に対応しておらず,僕自身プラグイン開発の知見も全くないので諦めた.他に何かないか探していたところ,たまたまTwitterkeypatchが流れてきたのでまずこれを導入することにした.keypatchにはkeystoneが必要なので,まずIDA Pythonでkeystoneを使えるようにする.

しかしこれがなかなかやっかいで,IDA Pythonはシステム標準のもの (/usr/bin/python) を使う.僕は普段pyenvを使っているためmacOSのpipを一切整えておらず,いざ導入してもSIP (System Integrity Protection) に阻まれて一切のパッケージをインストールできない.もちろんSIPを無効化する方法 (http://icchy.hatenablog.jp/entry/2016/05/16/121630) もあるのだが,なんだか面倒なのでpyenvをうまく使う方法を考えた.

まずIDA Pro本体のディレクトリ (macOSでは/Applications/IDA Pro 7.0/ida.app/Contents/MacOS) におけるファイル・ディレクトリは次のようになっている.

...
cfg/ # 各バイナリ用のIDA設定ファイル
dbgsrv/ # 各種アーキテクチャ用のdbgsrvバイナリ
ida # 32bitバイナリ用IDA
ida64 # 64bitバイナリ用IDA
idc/ # idcスクリプト
plugins/ # プラグイン
python/ # IDA Python用ライブラリ
sig/ # シグネチャデータ
...

プラグインにとって重要なのはpluginsおよびpythonディレクトリで,pluginsにはプラグイン本体のプログラムが,pythonにはIDA Pythonから使用するライブラリが入っている. 原理的にはpythonにimportしたいものがあれば良いので,そこに~/.pyenv/versions/2.7.14/lib/python2.7/site-packages/keystoneへのシンボリックリンクを張ればちゃんとimportできる.ただしライブラリをインストールするたびに作業が発生するので面倒だし,大量のライブラリに依存するパッケージがあったらかなり手間がかかる.

そこでpyenv-virtualenvに着目する.virtualenvは本来特定のディレクトリ以下にpythonのライブラリを閉じ込めるもので,site-packagesの位置をコントロールすることでライブラリの名前空間を切り替えている.普通はshellのsourceコマンドなどでactivateするが,もちろんpythonのプログラム中からvirtualenvをactivateする方法はあって,bin/activate_this.pyを実行すればよい. これでida用のvirtualenvを切って,そこに必要なライブラリを入れていけば普段の環境は汚さずに済むしちゃんとpipでインストールできるので解決する. あとはこれをidaの起動時に実行されているようにしなければならないが,python以下を眺めていたらinit.pyというファイルを見つけた.このファイルの最後の方に

# Load the users personal init file
userrc = os.path.join(ida_diskio.get_user_idadir(), "idapythonrc.py")
if os.path.exists(userrc):
    ida_idaapi.IDAPython_ExecScript(userrc, globals())

こんなコードがあって,いろいろ調べるとどうやら起動時に$HOME/.idapro/idapythonrc.pyを実行してくれることがわかった.あとはこのファイルの中にpyenv-virtualenvの適当な環境をactivateするコードを書けばよい.

activate_this = '/Users/icchy/.pyenv/versions/2.7.14/envs/ida/bin/activate_this.py'
execfile(activate_this, dict(__file__=activate_this))

これでpyenvのidaという名前の環境がIDA Pythonに適用され,無事にkeypatchを導入することができた. ただし一つだけ注意しておく必要があるのはIDA Pythonの実行バイナリが変わっていないため,実行されるpythonのバージョンが必ずしもライブラリの導入環境と一致するわけではないということ.もちろんpyenv側でsystemと同じものを用意して,その下にvirtualenvを切ればよい話なんだけどまあ2.7系だし多分大丈夫でしょう.みたいな気持ち.

idasecを導入する

あとntddkのブログにidasecの7.0用パッチを書いた話をたまたま見かけて,貼られていた動画が面白そうだったので導入することにした.

これもハマりまくって結構時間を溶かしたんだけど,細かく書くのが面倒になってきたので要点だけ述べると,

  • binsecを動かすのに結構ライブラリが必要なのでntddk/binsec-vagrantを丸パクリしてbinsec-dockerを書いた
  • PyQt5の導入をするときにbrewでやるとpython3用が入ってIDAから使えなくなるのでbrew install pyqt5 --without-python3でやるとうまくいく
  • idasecのディレクトリでmakeを叩くのを忘れない (UIが生成されない)
  • pip install protobuf pyzmq capstone graphviz pyparsing enum path.py plotly
  • idasecはライブラリになっていないのでIDAのpython以下にidasecを配置しておく

ちなみに適当なバイナリでidasec試したんだけど,pythonが途中でUnicodeEncodeError吐いてIDAがハングアップした.pythonはカス