СниферАвтор:
GriYo / 29A
Перевод:
_follower / TPOC
Windows 2000 представляют новую
возможность для пользователей: возможность создания сырых гнезд. Мы будем
использовать эту новую способность Windows, чтобы захватить пакеты сети. Что
делать с захваченными пакетами - ваше решение. Рассмотрим некоторые возможности:
* захватить login/password и используют их позже для доступа к соответствующим
услугам.
* чтобы получить команды от Вашего удаленного сервера. Эти команды могут
отосланы посредством TCP, UDP или ICMP протоколов, или даже комбинацией их. Есть
и ограничения. Только пользователь с привилегиями Администратора могут создать
сырые гнезда. Прежде всего мы должны инициализировать гнезда Windows, вызывая
процедуру WSASTARTUP. Мы сообщим процедуре WSASTARTUP, что мы нуждаемся в
Winsock версии 2.2 +, так как только эта версия подходит для нашей задачи.
Поэтому стоит подумать о переходе на ОС Windows 2000 или XP и выше.
invoke WSAStartup,00000202h,addr wsaDATA
.if eax != 0
;Error: WSAStartup
jmp ExitApp
.endif |
Второй шаг состоит в том, чтобы создать
гнездо, в режиме - «слушать все». Не плохая идея в том чтобы выполнять этот код
в отдельной нити, так что его выполнение не беспокоит остальная часть
приложения.
WSA_FLAG_OVERLAPPED equ 00000001h
WSockThread proc pParam :DWORD
LOCAL s :SOCKET
LOCAL if0 :sockaddr_in
LOCAL optval :DWORD
LOCAL dwBytesRet :DWORD
LOCAL dwFlags :DWORD
LOCAL wbuf[8] :BYTE
invoke WSASocket,
AF_INET,
SOCK_RAW,
IPPROTO_IP,
0,
0,
WSA_FLAG_OVERLAPPED
.if eax == INVALID_SOCKET
;Error: WSASocket
return 0
.endif
mov s,eax
invoke ZeroFill,addr if0,SIZE sockaddr_in
invoke WSockGetInterfase,
s,
addr if0,
0
.if eax == 0
;Error: GetInterface
return 0
.endif |
В упомянутом выше коде есть вызов
функции под названием WSockGetInterfase(). Не ищите ее среди сетевых функций
Winsock. Код этой функции – это наш следующий шаг. WSockGetInterfase
используется, чтобы получить списка доступных IP- адресов сетевых интерфейсов,
т.к. компьютер может иметь более одного ip-адреса (а в обычном случае даже два -
loopback - 127.0.0.1 и адрес сетевого интерфейса.) Чтобы получить их, мы будем
использовать параметр SIO_ADDRESS_LIST_QUERY Winsock IOCTL:
SIO_ADDRESS_LIST_QUERY equ 48000016h
WSockGetInterfase proc s:SOCKET, ifx :DWORD,num:DWORD
LOCAL BytesRet :DWORD
LOCAL if_LIST[2048] :BYTE
invoke ZeroFill,addr if_LIST,2048
mov BytesRet,0
invoke WSAIoctl,
s,
SIO_ADDRESS_LIST_QUERY,
NULL,
0,
addr if_LIST,
2048,
addr BytesRet,
NULL,
NULL
.if eax == SOCKET_ERROR
;Error: WSAIoctl
return 0
.endif
mov ecx,num
lea esi,if_LIST
cld
lodsd
.if eax == 0
;Error: No interface found
return 0
.elseif ecx >= eax
;Error: Device number too high
return 0
.endif
shl ecx,3
add esi,ecx
cld
lodsd
add eax,sockaddr_in.sin_addr
mov esi,eax
mov edi,ifx
add edi,sockaddr_in.sin_addr
cld
lodsd
stosd
return 1
WSockGetInterfase endp |
Мы вызываем функцию WSAIoctl() с
параметром SIO_ADDRESS_LIST_QUERY, чтобы получить список локальных сетевых IP -
адресов, с которыми можем связать наш сокет. Структура, на выходе, имеет
следующий формат:
SOCKET_ADDRESS_LIST STRUCT
iAddressCount dd ?
Address dd ?
SOCKET_ADDRESS_LIST ENDS |
WSockGetInterfase() использует 3 входных параметра:
* активное гнездо (s)
* указатель на структуру sockaddr_in, которая будет заполнена информацией
относительно отобранного интерфейса сети
* номер интерфейса, с которым мы связываемся. Мы используем здесь 0 чтобы
использовать первый обнаруженный интерфейс.
Как только мы создали гнездо и выбрали интерфейс (IP – адрес), мы можем связать
гнездо и интерфейс вызовом функции bind().
mov if0.sin_family,AF_INET
invoke htons,0
mov if0.sin_port,ax
invoke bind,
s,
addr if0,
SIZE sockaddr_in
.if eax == SOCKET_ERROR
;Error: bind
return 0
.endif |
Заключительный шаг – вызов функции
WSAIoctl()с параметром SIO_RCVALL. Посмотрим, что MSDN Библиотека говорит
относительно этой IOCTL:
SIO_RCVALL:
Позволяет гнезду получить все IP пакеты на сети.
Функция WSAIoctl принимает:
указатель сокета,
тип сетевого интерфейса AF_INET,
тип гнезда SOCK_RAW
IPPROTO_IP тип протокола.
Гнездо также должен быть связано с рабочим локальным интерфейсом, что означает,
что вы не можете использовать тип протокола - INADDR_ANY. Как только гнездо
связано , запросы к WSARecv() или Recv() функции возвращают IP датаграммы
проходящие через данный сетевой интерфейс. Обратить внимание на то, что Вы
должны выделить достаточно большой буфер. Установка этого IOCTL требует
привилегии Администратора на локальной машине. Константа SIO_RCVALL доступна в
Windows 2000 и более поздних версиях. Если все понятно как ясный день, то
применим это.
SIO_RCVALL equ 98000001h
mov dwBytesRet,0
mov optval,1
invoke WSAIoctl,
s,
SIO_RCVALL,
addr optval,
4,
0,
0,
addr dwBytesRet,
0,
0
.if eax == SOCKET_ERROR
;Error: WSAIoctl
return 0
.endif |
Теперь, в результате выполнения WSARecv()
на этом гнезде мы получим IP пакеты. Посмотрим пример:
lea edi,wbuf
cld
mov eax,PACKET_BUFFER_SIZE
stosd
lea eax,pcap_buffer
stosd
mov dwBytesRet,0
mov dwFlags,0
invoke WSARecv,
s,
addr wbuf,
1,
addr dwBytesRet,
addr dwFlags,
0,
0
.if eax == SOCKET_ERROR
;Error: WSARecv
return 0
.endif
;Decode IP header!
invoke DecodeIpHeader,addr wbuf |
Функция DecodeIpHeader() использует
указатель на структуру WSABUF, которая содержит информацию о захваченном сетевом
пакете. Давайте посмотрим пример того как нам извлечь из полученных пакетов
интересную информацию.
IP_HEADER STRUCT
Version_and_HdrLen db ?
ServiceType db ?
TotalLen dw ?
ID dw ?
Flags_and_FragOff dw ?
TimeToLive db ?
Protocol db ?
HdrChksum dw ?
SrcAddr dd ?
DstAddr dd ?
IP_HEADER ENDS
DecodeIpHeader proc Buffer:DWORD
LOCAL szSrcIp[16] :BYTE
mov eax,Buffer
mov esi,[eax+4] ;Точка буфера в структуре WSABUF
mov eax,[esi+IP_HEADER.DstAddr]
; Сделаем что-нибудь здесь с ip-адресом назначения
; ...
; ...
; ...
mov eax,[esi+IP_HEADER.SrcAddr]
;или сделать что-нибудь, используя ip-адрес источника данных
; ...
; ...
; ...
mov al,[esi+IP_HEADER.Protocol]
; Вы можете также проверить на определенные протоколы
.if al == IPPROTO_TCP
;...
;...
;...
.elseif al == IPPROTO_UDP
;...
;...
;...
.elseif al == IPPROTO_ICMP
;...
;...
;...
.endif
ret
DecodeIpHeader endp |
Пусть все народы,
счастливо храпят!
--
GriYo / 29A
Я не в бизнесе ...
... Я – бизнес
[C] GriYo / 29A, пер. _follower/TPOC | Новые события из жизни нашей лаборатории Статьи и переводы лаборатории TPOC Программы лаборатории TPOC Здесь мы сообщаем Вам, какие творения скоро появятся Ссылки на сайты, где можно найти больше информации История нашей лаборатории и ее члены |