前提・実現したいこと
「たのしいバイナリの歩き方」という本を参考に勉強をしています。
C言語で配列に入れたシェルコードを実行しようとしているのですが、実行に失敗します。
具体的には、システムコールを呼び出す部分 int 0x80が実行がスキップされてしまいます。
どなたかご教授お願いいたします。
発生している問題・エラーメッセージ
Program received signal SIGSEGV, Segmentation fault.
0x0804a061 in ?? ()
該当のソースコード
コンパイル前のc言語でのソースコードはこちらです。
ファイル名はsample7.cです。
c
1unsigned char shellcode[] = { 2 0x31, 0xc0, // xor %eax, %eax 3 0x50, // push %eax 4 0x89, 0xe0, // mov %esp, %eax 5 0x83, 0xe8, 0x0c, // sub $0x0c, %eax 6 0x50, // push %eax 7 0x89, 0xe3, // mov %esp, %ebx 8 0x68, 0x2f, 0x73, 0x68, 0x00, // push $0x68732f 9 0x68, 0x2f, 0x62, 0x69, 0x6e, // push $0x6e69622f 10 0x89, 0xe2, // mov %esp, %edx 11 0x31, 0xc0, // xor %eax, %eax 12 0x50, // push %eax 13 0x53, // push %ebx 14 0x52, // push %edx 15 0x50, // push %eax 16 0xb0, 0x3b, // mov $0x3b, %al 17 0xcd, 0x80, // int $0x80 18}; 19 20int main(void) 21{ 22 void (*p)(void); 23 p = (void(*)())shellcode; 24 p(); 25 return 0; 26}
以下のコマンドでコンパイルしました。
#gcc -Wall -m32 -fno-stack-protector -fno-asynchronous-unwind-tables -z execstack -g sample7.c -o sample7
試したこと
まず、実行権限を与えて実行した結果は以下になります。
$ ./sample7 Segmentation fault
fileコマンドでバイナリを調べました
$ file sample7 sample7: setuid ELF 32-bit LSB executable, Intel 80386, version 1 (SYSV), dynamically linked (uses shared libs), for GNU/Linux 2.6.24, BuildID[sha1]=0xf5a9899dfa70c47141d86c76067829a81ab73fab, not stripped
次にgdbで処理を1行ずつ確認しました。
$ gdb sample7 GNU gdb (Ubuntu/Linaro 7.4-2012.02-0ubuntu2) 7.4-2012.02 Copyright (C) 2012 Free Software Foundation, Inc. ...省略... This GDB was configured as "i686-linux-gnu". For bug reporting instructions, please see: <http://bugs.launchpad.net/gdb-linaro/>... Reading symbols from /home/tk/target/sample7...done. (gdb) disas main Dump of assembler code for function main: 0x080483b4 <+0>: push %ebp 0x080483b5 <+1>: mov %esp,%ebp 0x080483b7 <+3>: and $0xfffffff0,%esp 0x080483ba <+6>: sub $0x10,%esp 0x080483bd <+9>: movl $0x804a040,0xc(%esp) 0x080483c5 <+17>: mov 0xc(%esp),%eax 0x080483c9 <+21>: call *%eax 0x080483cb <+23>: mov $0x0,%eax 0x080483d0 <+28>: leave 0x080483d1 <+29>: ret End of assembler dump. (gdb) b *0x080483c9 ; call *%eax の部分にブレークポイントをセット Breakpoint 1 at 0x80483c9: file sample7.c, line 24. (gdb) b *0x080483cb ; mov $0x0,%eax の部分にブレークポイントをセット Breakpoint 2 at 0x80483cb: file sample7.c, line 25. (gdb) run Starting program: /home/tk/target/sample7 Breakpoint 1, 0x080483c9 in main () at sample7.c:24 ; call *%eaxの部分で止まる 24 p(); (gdb) si ; shellcode内部に入る 0x0804a040 in shellcode () (gdb) disas shellcode Dump of assembler code for function shellcode: => 0x0804a040 <+0>: xor %eax,%eax 0x0804a042 <+2>: push %eax 0x0804a043 <+3>: mov %esp,%eax 0x0804a045 <+5>: sub $0xc,%eax 0x0804a048 <+8>: push %eax 0x0804a049 <+9>: mov %esp,%ebx 0x0804a04b <+11>: push $0x68732f 0x0804a050 <+16>: push $0x6e69622f 0x0804a055 <+21>: mov %esp,%edx 0x0804a057 <+23>: xor %eax,%eax 0x0804a059 <+25>: push %eax 0x0804a05a <+26>: push %ebx 0x0804a05b <+27>: push %edx 0x0804a05c <+28>: push %eax 0x0804a05d <+29>: mov $0x3b,%al 0x0804a05f <+31>: int $0x80 End of assembler dump. (gdb) b *0x0804a05f ; 最終行 int $0x80にブレークポイントをセット Breakpoint 3 at 0x804a05f (gdb) c Continuing. Breakpoint 3, 0x0804a05f in shellcode () ; int 0x80の前で処理が止まる (gdb) disas shellcode Dump of assembler code for function shellcode: 0x0804a040 <+0>: xor %eax,%eax 0x0804a042 <+2>: push %eax 0x0804a043 <+3>: mov %esp,%eax 0x0804a045 <+5>: sub $0xc,%eax 0x0804a048 <+8>: push %eax 0x0804a049 <+9>: mov %esp,%ebx 0x0804a04b <+11>: push $0x68732f 0x0804a050 <+16>: push $0x6e69622f 0x0804a055 <+21>: mov %esp,%edx 0x0804a057 <+23>: xor %eax,%eax 0x0804a059 <+25>: push %eax 0x0804a05a <+26>: push %ebx 0x0804a05b <+27>: push %edx 0x0804a05c <+28>: push %eax 0x0804a05d <+29>: mov $0x3b,%al => 0x0804a05f <+31>: int $0x80 End of assembler dump. (gdb) si ; int $0x80でシステムコールが実行されるはず・・・ 0x0804a061 in ?? () ; 実行されずプログラムカウンタが進んだ (gdb) x/i *0x0804a061 0x0: Cannot access memory at address 0x0 (gdb) si Program received signal SIGSEGV, Segmentation fault. 0x0804a061 in ?? ()
知識が足りず、どのようにして対処すればよいのかわからない状態です。
int $0x80のシステムコールが無視されてしまうので、なにか対処法を教えていただきたいです。
補足情報(FW/ツールのバージョンなど)
OS : Ubuntu 12.04 LTS 32bit
32bitであることは、コマンドでも確認しました。
$ cat /etc/lsb-release DISTRIB_ID=Ubuntu DISTRIB_RELEASE=12.04 DISTRIB_CODENAME=precise DISTRIB_DESCRIPTION="Ubuntu 12.04 LTS" $ uname -a Linux tk-VirtualBox 3.2.0-126-generic-pae #169-Ubuntu SMP Fri Mar 31 14:43:09 UTC 2017 i686 i686 i386 GNU/Linux
gcc (Ubuntu/Linaro 4.6.3-1ubuntu5) 4.6.3
GNU gdb (Ubuntu/Linaro 7.4-2012.02-0ubuntu2) 7.4-2012.02
回答1件
あなたの回答
tips
プレビュー
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。
2020/08/02 06:41 編集
2020/08/02 08:18
2020/08/02 08:39