Nootropic.me

Return-to-Registerまとめ

※この記事は管理人のメモです。

ASLRのbypass手法はいくつかあるが今回はReturn-to-Register(RtR)について挙げる。

環境はBacktrack5を使用する。
今回は下のソースコードを使う。


/*rtrtest.c*/
#include <stdio.h>
#include <string.h>

void vuln(char *pass){
        char buf[512];
            strcpy(buf,pass);
}
int main(int argc,char** argv){
        vuln(argv[1]);
            return 0;
}

見れば分かるとは思うがvuln関数にはバッファオーバーフローの脆弱性が存在する。
ここでASLRが効いていない場合は比較的容易に任意のコードを実行できるが有効だった場合は一工夫要る。


セキュリティ機構

セキュリティ機構は以下のようになっている。


NX有効。


ASLR有効。


スタックの構造把握


リターンアドレスまでの距離524バイト。
524+リターンアドレス(4バイト)=528
528バイトでリターンアドレスを埋められる。


関数の逆アセンブル結果


main関数の逆アセンブル結果。


vuln関数の逆アセンブル結果。


ブレークポイントの設置


vuln関数の
0x080483e4 push ebp
0x08048403 ret
にブレークポイントを仕掛ける。


流れ把握


vuln関数のpush ebp命令実行直前。「0x0804841d」がvuln関数のリターンアドレスとなる。


vuln関数のret命令実行直前。「0x42424242」がリターンアドレスとなる。


ret命令実行後。
eaxレジスタには「0x41414141」の値が入る。
eaxレジスタに任意の値を入れられるならばここでリターンアドレスに「jmp eax」ないし「call eax」のアドレスが入っていれば任意のコードを実行できる?


使用する命令の選択


Ubuntu(BacktrackはUbuntuベース)ではASLRはtextセクションのランダマイズを行わないのでこのアドレスは不変。
今回はアドレス「0x080483df」に存在する「call eax」命令を使用することにする。


Exploitコード


msfpayloadで生成しただけのやつ。
こんな感じでvuln関数のリターン先を「0x080483df」にする。
ここでリトルエンディアンなことを忘れない。


シェル起動


ここでespレジスタを見ると「0x080483df」が格納されている事がわかる。
「0x90909090」がeaxレジスタに入り「call eax」が実行される。



シェルの立ち上げに成功。
尚、元からroot権限なので特に感動がない模様。


追記:
2013/9/22:AsciiArmor有効のPCで「call eax」命令を探したところNULLバイトが含まれていなかったのでもしかすると ASLR+AsciiArmorに対しても有効かもしれません。現在未確認です。


Author:ラロ