우리 집에 GDB 있는데 메모리 보고 갈래? (3)
3에서는 소스 파일이 없다 가정한 상태로 ida, gdb를 이용해 취약점을 찾고 exploit을 진행한다.
보통 정적 분석은 ida, 동적 분석은 gdb를 활용한다고 한다.
ida hexray가 제대로 작동하지 않아서 (完)우리집에 GDB 있는데… 메모리 보고갈래?(3)의 사진을 참고했다.
보면 거의 비슷하게 코드가 디컴파일 된 것을 볼 수 있다. ㄷㄷ
보면 strcpy로 인자로 입력된 문자열을 v4에 넣어주는데, argv[1]을 복사할 때 버퍼를 검사하는 로직이 없다. v4, v5는 지역 변수이므로 스택에 있기에 스택 오버플로우가 일어날 수 있는 것이다. v5가 1이 되면 쉘을 열 수 있으므로 스택 오버플로우로 v5의 값에 접근하면 될 것 같다.
gdb에서 동적으로 확인해 보면 strcpy 전 스택에서 0xffffcff0이 v4, 0xffff4가 argv[1]이고, strcpy 호출 후 argv[1]의 값이 v4로 잘 복사되는 것을 볼 수 있다.
우리 집에 gdb 있는데 메모리 보고 갈래 3과는 아무래도 빌드 환경이 달라 코드도 다른거 같아서, 내 코드 기준으로 정리해보겠다. 참고한 글에서는 mov로 esp 주소에 eax 값을 옮겨준 것과 달리 내 코드에서는 push로 스택에 직접적으로 넣어주는데, 이는 컴파일러 버전의 차이가 아닌가 생각이 든다.
어쨌든 push를 통해 eax에 전달받은 인자(v4, v5)를 스택에 넣어주는 코드고, 그 전을 보면 +70에 lea eax, [ebp-0x26] 이라는 코드가 있다. 이 코드를 봤을 때 v4 변수의 주소는 ebp-26이라는 것을 알 수 있고, 이 주소를 eax에 전달한 후 push로 ebp-26 주소를 스택에 넣어주는 것을 알 수 있다.
다음으로 분기부분을 보면 ebp-0x1c(v5)의 값이 1과 같는지 검사하고 같지 않다면 +128로 점프, 같다면 syscall을 이용해 /bin/bash 쉘을 실행하는 것 같다.
주석을 보면 main의 stackframe 기준으로 v4, v5 변수가 각각 스택의 어디에 있는지를 알 수 있다.
위 스택 사진처럼 v4의 값이 넘친다면 v5에 영향을 미칠 수 있다.
계산을 해보니 v4, v5 간의 거리가 A(10)이므로 v4영역에 10 바이트 만큼의 아무 값이나 채운 후, v5 영역이 1이 되도록하면 될 것 같다.
A*10 만큼 채우고 v5가 int형이니 4바이트 크기로 1을 넣어줬는데 쉘이 뜨지 않았다. 이렇게 왜 exploit 안됐는지 모르는 경우에는 gdb를 이용해서 동적 디버깅을 해보면 된다.
확인해보니 정수 00000001 대신 문자열 "00000001"이 들어가서 아스키 코드 값으로 변해버렸다..
이럴 경우에는 파이썬, 펄 등의 언어로 16진수의 값을 넣어주면 된다.
python의 -c 옵션을 사용하면 command line으로 출력이 가능하고 \x를 써주면 hex 표현도 가능하기 때문에 딱 적합하다.
exploit 할 때는 쉘 커맨드의 출력 값을 리턴해주는 `(백틱) 문자로 반드시 python -c 부터 파이썬 코드 끝까지 감싸줘야한다.
파이썬 코드 내용은 'A'를 10번 출력해 v4 스택을 꽉차게 하고 거기에 16진수 \x00\x00\x00\x01로 v5에 00000001을 넣어준 것이다.
'Old (2021.01 ~ 2021.12) > Pwnable' 카테고리의 다른 글
Return Address Overwrite (0) | 2021.07.11 |
---|---|
Buffer Overflow (0) | 2021.07.04 |
[Linux-x86] shellcode 제작 (0) | 2021.06.26 |
우리 집에 GDB 있는데 메모리 보고 갈래? (2) (0) | 2021.03.13 |
우리 집에 GDB 있는데 메모리 보고 갈래? (1) (0) | 2021.03.10 |