GB | BIG5
|
| 首頁 > 安全技術 > 程序 > 正文 |
 |
| 非安全編程演示之高級緩沖區溢出篇 |
| 本文出自:http://xfocus.org/ 作者:alert7(alert7@netguard.com.cn) (2002-08-08 06:02:00) |
聲明:文中的大部分演示程序來自qera <gera@core-sdi.com>,感謝qera為
我們精心構造這些很能說明的演示程序。
有些程序可能有不只一種的利用方法,而文中又沒有提到的。如果您有
好的idea,記得mailto:alert7@xfocus.org,不正確或者不當之處還
請斧正。
★★ 一 高級緩沖區溢出篇
★ 1.1 演示一----盲目服從(blind obedience)
定義的buf太小,需要copy的數據不足以容納下。
/* abo1.c *
* specially crafted to feed your brain by gera@core-sdi.com */
/* Dumb example to let you get introduced... */
int main(int argc,char **argv) {
char buf[256];
strcpy(buf,argv[1]);
}
這是個很好的例子程序,很能說明問題:該程序將拷貝argv[1]到buf中,使用了
strcpy函數,沒有做任何的邊界檢查。這就給了我們一個機會,傳一個超長的
argv[1]進去,覆蓋到堆棧中buf面的數據。你需要利用所有的工具來查看
buf面到底是什重要的東西,然才能構造出那些exploit需要的摸板。
★ 1.2 演示二----執行流程(execution flow)
在來看看這個程序
/* abo2.c *
* specially crafted to feed your brain by gera@core-sdi.com */
/* This is a tricky example to make you think *
* and give you some help on the next one */
int main(int argv,char **argc) {
char buf[256];
strcpy(buf,argc[1]);
exit(1);
}
正如我們看的那樣,在這個例子中,加了個exit(). 發現了不同了嗎?一般利用覆蓋
main的返回地址的方法已經行不通了。在這個例子中,windows下利用windows的異常
機制可以成功的溢出這個程序,而在unix下就沒有這種特性,暫時還不知道如何溢出
這個程序?或者就根本不能利用。歡迎討論,請mailto:alert7@xfocus.org :)
★ 1.3 演示三----覆蓋函數指針
/* abo3.c *
* specially crafted to feed your brain by gera@core-sdi.com */
/* This'll prepare you for The Next Step */
int main(int argv,char **argc) {
extern system,puts;
void (*fn)(char*)=(void(*)(char*))&system;
char buf[256];
fn=(void(*)(char*))&puts;
strcpy(buf,argc[1]);
fn(argc[2]);
exit(1);
}
可利用緩沖區溢出覆蓋fn函數指針,達到攻擊目的。
★ 1.4 演示四----覆蓋指針,導致任意地址的覆蓋
/* abo4.c *
* specially crafted to feed your brain by gera@core-sdi.com */
/* After this one, the next is just an Eureka! away */
extern system,puts;
void (*fn)(char*)=(void(*)(char*))&system;
int main(int argv,char **argc) {
char *pbuf=malloc(strlen(argc[2])+1);
char buf[256];
fn=(void(*)(char*))&puts;
strcpy(buf,argc[1]);
strcpy(pbuf,argc[2]);
fn(argc[3]);
while(1);
}
第一個strcpy時候,可覆蓋到pbuf指針,可使pbuf指向fn地址,所以第二次
strcpy的時候就會覆蓋到fn指針,結果運行fn()函數的時候就可以執行任意
函數調用,比如system();
★ 1.5 演示五----ch-ch-ch-changes
/* abo5.c *
* specially crafted to feed your brain by gera@core-sdi.com */
/* You take the blue pill, you wake up in your bed, *
* and you believe what you want to believe *
* You take the red pill, *
* and I'll show you how deep goes the rabbit hole */
int main(int argv,char **argc) {
char *pbuf=malloc(strlen(argc[2])+1);
char buf[256];
strcpy(buf,argc[1]);
for (;*pbuf++=*(argc[2]++););
exit(1);
}
第一個strcpy時候,可覆蓋到pbuf指針,可使pbuf指向exit的GOT或者.dotrs地址+4,
從而可以覆蓋到那些部分,獲得控制權。
★ 1.6 演示六
/* abo6.c *
/* specially crafted to feed your brain by gera@core-sdi.com */
/* wwwhat'u talkin' about? */
int main(int argv,char **argc) {
char *pbuf=malloc(strlen(argc[2])+1);
char buf[256];
strcpy(buf,argc[1]);
strcpy(pbuf,argc[2]);
while(1);
}
第一個strcpy時候,可覆蓋到pbuf指針,可使pbuf指向第二個strcpy函數的返回地址,
從而可以覆蓋到該地址,第二個strcpy一返回就可以獲得控制權。
★ 1.7 演示七
/* abo7.c *
* specially crafted to feed your brain by gera@core-sdi.com */
/* sometimes you can, *
* sometimes you don't *
* that's what life's about */
char buf[256]={1};
int main(int argv,char **argc) {
strcpy(buf,argc[1]);
}
[alert7@redhat]$ gcc -o test test.c -g
[alert7@redhat]$ gdb test -q
(gdb) l
1 char buf[256]={1};
2
3 int main(int argv,char **argc) {
4 strcpy(buf,argc[1]);
5 }
(gdb) b 4
Breakpoint 1 at 0x80483cb: file test.c, line 4.
(gdb) r 999
The program being debugged has been started already.
Start it from the beginning? (y or n) y
Starting program: /home/alert7/test 999
Breakpoint 1, main (argv=2, argc=0xbffffbc4) at test.c:4
4 strcpy(buf,argc[1]);
(gdb) p &buf
$1 = (char (*)[256]) 0x8049460
buf的地址為0x8049460,也就是說如果0x8049460地址有什重要的話我們
可以得到控制權的數據的話,那我們就可以溢出成功。
在這裡:
[alert7@redhat]$ objdump -s -j .dtors test
test: file format elf32-i386
Contents of section .dtors:
804956c ffffffff 00000000 ........
我們可以覆蓋.dtors,達到獲得控制權的目的。
★ 1.8 演示八
Don't stay static
/* abo8.c *
* specially crafted to feed your brain by gera@core-sdi.com */
/* spot the difference */
char buf[256];
int main(int argv,char **argc) {
strcpy(buf,argc[1]);
}
[alert7@redhat]$ gcc -o test test.c -g
[alert7@redhat]$ objdump --dynamic-reloc test
test: file format elf32-i386
DYNAMIC RELOCATION RECORDS
OFFSET TYPE VALUE
0804947c R_386_GLOB_DAT __gmon_start__
0804946c R_386_JUMP_SLOT __register_frame_info
08049470 R_386_JUMP_SLOT __deregister_frame_info
08049474 R_386_JUMP_SLOT __libc_start_main
08049478 R_386_JUMP_SLOT strcpy
[alert7@redhat]$ gdb test -q
(gdb) l
1
2 char buf[256];
3
4 int main(int argv,char **argc) {
5 strcpy(buf,argc[1]);
6 }
7
(gdb) b 5
Breakpoint 1 at 0x80483cb: file test.c, line 5.
(gdb) r 11
Starting program: /home/alert7/test 11
Breakpoint 1, main (argv=2, argc=0xbffffbc4) at test.c:5
5 strcpy(buf,argc[1]);
(gdb) p & buf
$1 = (char (*)[256]) 0x8049540
(gdb) q
The program is running. Exit anyway? (y or n) y
[alert7@redhat]$ objdump -s -j .dtors test
test: file format elf32-i386
Contents of section .dtors:
8049458 ffffffff 00000000 ........
[alert7@redhat]$ gcc -o test test.c -g -static
[alert7@redhat]$ gdb test -q
(gdb) l
1
2 char buf[256];
3
4 int main(int argv,char **argc) {
5 strcpy(buf,argc[1]);
6 }
7
(gdb) b 5
Breakpoint 1 at 0x804819b: file test.c, line 5.
(gdb) r 11
Starting program: /home/alert7/test 11
Breakpoint 1, main (argv=2, argc=0xbffffc14) at test.c:5
5 strcpy(buf,argc[1]);
(gdb) p &buf
$1 = (char (*)[256]) 0x807bb60
(gdb) p __exit_funcs
$2 = (struct exit_function_list *) 0x807b160
[alert7@redhat62 alert7]$ objdump -s -j .dtors test
test: file format elf32-i386
Contents of section .dtors:
807b100 ffffffff 00000000 ........
buf的地址都比其他的地址要大,所以覆蓋不到他們。
這個例子還不知道如何得到控制權呢?用超長字符串覆蓋main函數的
返回地址是不現實的,並且在還沒有覆蓋到main函數返回地址之前就會
Segmentation fault,原因是訪問了一個沒有映射的地址(地址
映射是不連續的) 。
這個演示程序讓我鬱悶了好久,在我的linux上還真的無法成功溢出這個
程序,還是qera又一次專門為windows設計的!?(如果您有好的idea,
記得mailto:alert7@xfocus.org)。在windows下成功溢出這個演示程
序是沒有問題的。
★ 1.9 演示九----兩次free技術
/* abo9.c *
* specially crafted to feed your brain by gera@core-sdi.com */
/* free(your mind) */
/* I'm not sure in what operating systems it can be done */
int main(int argv,char **argc) {
char *pbuf1=(char*)malloc(256);
char *pbuf2=(char*)malloc(256);
gets(pbuf1);
free(pbuf2);
free(pbuf1);
}
請參考waring3的<<一種新的Heap區溢出技術分析>>
那片文章上已經講的很明白了,不想多說,不想做重復的勞動:)
★ 1.10 演示十----一次free技術
/* abo10.c *
* specially crafted to feed your brain by gera@core-sdi.com */
/* Deja-vu*/
char buf[256];
int main(int argv,char **argc) {
char *pbuf=(char*)malloc(256);
gets(buf);
free(pbuf);
}
[alert7@redhat]$ gcc -o test test.c -g
/tmp/ccO6gW96.o: In function `main':
/home/alert7/test.c:6: the `gets' function is dangerous and should not be used.
[alert7@redhat]$ gdb test -q
(gdb) l
1 char buf[256];
2
3 int main(int argv,char **argc) {
4 char *pbuf=(char*)malloc(256);
5
6 gets(buf);
7 free(pbuf);
8 }
(gdb) b 6
Breakpoint 1 at 0x8048440: file test.c, line 6.
(gdb) r
Starting program: /home/alert7/test
Breakpoint 1, main (argv=1, argc=0xbffffbc4) at test.c:6
6 gets(buf);
(gdb) p &buf
$1 = (char (*)[256]) 0x80495c0
(gdb) p pbuf
$2 = 0x80496c8 ""
可覆蓋到pbuf的chunk塊,利用一次free技術也可覆蓋到.dotrs,main的返回地址等等。
演示九和演示十都是由緩沖區溢出而導致的內存管理函數處理出錯,從而利用內存管理
函數中的寫操作,覆蓋到自己想要覆蓋的任何地址空間。
(http://www.fanqiang.com)
進入【UNIX論壇】
|
|
| 相關文章 |
如何編寫自己的緩沖區溢出利用程序? (2002-07-26 13:31:26) C源碼:Linux的nfsd存在溢出漏洞允許入侵者遠程獲取root (2002-07-08 06:02:00) 部分防止Solaris溢出的方法 (2001-09-12 15:00:01) 緩沖區溢出:十年來攻擊和防衛的弱點 (2001-08-01 15:00:00) 不能登錄到CDE,出現錯誤:file table overflow(文件表溢出) (2001-05-30 07:00:00)
|
|
|
|
 |
★ 樊強制作 歡迎分享 ★ |