2019. 4. 27. 23:25ㆍSystem Hacking/ROP(64byte)
안녕하세요!
오늘은 ROP 64byte
문제 4번을 풀어보도록 하겠습니다!
파일은 제가 위에 놓도록 하겠습니다!
코드를 보니
지난 3번 문제와 달라진 게 있죠?
3번 문제에선 맨처음에 /bin/sh 문자열을 가진
sh[ ] 배열이 있었는데
이번 문제는 /bin/sh 문자열이 사라졌습니다!
바로 nothing 함수가 있네요!
asm volatile 함수는
제가 3번 문제에서 알려드렸듯이,
c언어에서 aseembly 코딩을 할 때 쓰는 함수 입니다!
그리고 vuln 함수는
3번 문제와 똑같네요!
버퍼는 16byte만 선언되었는데,
read 함수로 읽어오는 byte가
무려 256byte나 읽어오네요!
3번과 마찬가지로 버퍼 overflow 문제인데요!
달라진 점은
(1) /bin/sh가 없다는 것과!
(2) asm volatile( ) 함수의 인자가 바뀌었다는 것!
이것 말고는 나머지 3번과 완전 똑같습니다!
우선 vuln 함수를 peda로 까보았습니다!
나중에 저희가 vuln+42 ret
부분에 breakpoint 걸고
offset 계산해야겠죠?
물론 이론상으론 sub rsp,0x10(=16)이니
16byte + 8byte(ebp) = 24byte dummy
라는 걸 유추 할 수 있지만요!
nothing 함수의 경우 저희가 쓰고 싶은
pop rdi
pop rsi
pop rdx
이 gadget들은
nothing+4 부터 시작되네요!
그럼 저희가 이론적으로 24byte를 덮어써야 한다!
라고 추측을 해봤는데!
실제로는 얼만큼을 덮어써야 할지!
직접 검증해 보겠습니다!
제가 위에서 말씀드린대로 vuln+42 (ret) 부분에
breakpoint를 겁니다!
그리고
run을 해서
INPUT: 에다가
pwn cyclic 50 한 아래의 문자 값을 입력해줍니다!
입력을 하면 알아서
프로그램이 저희가 설정해둔 breakpoint에 걸리게 됩니다!
그리고 값을 확인해보니 0x61616167이 있네요!
그러면 이 값을 복사해서
offset을 계산해봅시다!
cyclic 50은 제가 아까 실행한 명령어구요!
여기서 제가 복사한 0x61616167을 형식에 맞게
" cyclic -l 0x61616167 "
입력하면 아래와 같이
24가 출력이 됩니다!
한마디로 3번 문제와 마찬가지로 24만큼 덮어씌우면
ret_address가 나온다 이 말이겠죠!
그래서 바로 exploit code 짜보러 가보겠습니다!
payload 부분부터 설명하겠습니다!
e , p , raw_input 부분은 이미 3번 문제에서
설명하였습니다!
payload는 우선 빈칸 ''으로 설정하구요!
저희가 cyclic -l 0x61616167을 통해
얻은 24의 값 (=더미값)
을 써줍니다!
그러면 이제 return address에는 무엇을 써야 할까요?
제가 혹시 위에서 말씀드린거 기억 나시나요?
/bin/sh 문자열이 존재하질 않아요!
저희가 어딘가에 적어야 해요!
그래서 저희는
"read 함수로 bss 영역에 /bin/sh 문자열을 적을 거에요!"
근데 read 함수의 인자를 세팅해주기 위해서
pop rdi
pop rsi
pop rdx
위에서 말한 이 gadget을 쓸겁니다
저희가 만들고 싶은 함수의 세팅
read( 0, bss, 8)
p64( ) 함수로
저희가 넣어야 하는 값들
(1) 0
(2) bss() ->주소
(3) 8 ->읽어들일 문자크기
왜 딱 8입니까? 라고
물으실 분들을 위해
준비했습니다!
/bin/sh 문자열 길이가 7입니다!
근데 저희가 enter를 치게 되면
1byte가 추가되어서!
총 8byte로 설정한겁니다!
그리고
read 함수가 끝나면 다시
pop rdi
pop rsi
pop rdx
을 쓸겁니다!
chaining이 가능하기 때문이죠!
그럼 이제는 무엇을 불러올 것이냐?
system("/bin/sh") 를 불러와야죠!
우선 gadget setting을
nothing +4 로 하구요!
첫 번째 인자에는 bss()에 적은 문자열
/bin/sh! 주소!
두 번째, 세 번째 인자는 없죠!
system( )함수에 /bin/sh만 넣을꺼라서요!
그래서 2,3번째는 모두 0으로 설정을 해줍니다!
그리고 ret에 system함수의 symbol을 읽어 들이면!
system("/bin/sh")가 완성이 됩니다!
밑에는 그냥
함수를 INPUT: 이 출력될때 까지 읽어라
그리고 우리가 작성한 payload를 보내라!
여기서 좀 헷갈릴 수가 있는데!
저희가 먼저 payload를 보내면,
read함수가 호출이 되죠?
저희가 맨처음에 /bin/sh를 적으려고 했으니까요!
그래서 read 함수가
"니가 넣고 싶은 값 적어"
라고 말하면
그때 /bin/sh를 보내는겁니다!
그래서 p.sendline("/bin/sh")를 한겁니다!
p.send("/bin/sh\00")으로도 보낼 수 있는데
p.sendline이 enter까지 같이 넣어서 보내줘서
p.sendline으로 보냈습니다!
이렇게 모든 payload를 잘 보내면
쉘이 획득 될 것이기에!
쉘과 상호작용 하기위해
p.interactive()까지 적으면
exploit이 완성됩니다!
고생하셨습니다!
'System Hacking > ROP(64byte)' 카테고리의 다른 글
ROP (64byte) 문제 3번 (0) | 2019.04.26 |
---|---|
ROP (64byte) 문제 2번 (0) | 2019.04.24 |
ROP (64byte) 문제 1번 (0) | 2019.04.22 |