подмена ip
они позволяют тебе самому формировать TCP\IP пакеты -- можешь вкладывать туда какой хошь IP\MAC адрес
...так а ответ и не нужен...
есть исходники...палазил в них немного, поразбирался, и оказалось что вроде как TCP (потоковый) пакет послать нельзя - только дейтограмму (хотя вроде как заголовок ТСР пакета там формируется)...так ли это или я ошибаюсь?
unit raw;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls, Winsock2;
type
TPcktBuf = Array[0..4095] of byte;
TForm1 = class(TForm)
SourceIP: TEdit;
SourcePrt: TEdit;
DestinIP: TEdit;
DestinPrt: TEdit;
PcktData: TEdit;
Label1: TLabel;
Label2: TLabel;
Label3: TLabel;
Label4: TLabel;
Label5: TLabel;
memo1: TMemo;
Button1: TButton;
procedure Button1Click(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
procedure SendIt;
end;
type
T_IP_Header = record
ipver : Byte;
ipts : Byte;
iplength : Word;
ipID : Word;
ipoffst : Word;
ipttl : Byte;
iptype : Byte;
ipcrc : Word;
ipscrIP : LongWord;
ipdestIP : LongWord;
end;
// А это хедер UDP пакета
Type
T_UDP_Header = record
src_portnumb : Word;
dst_portnumb : Word;
udp_len : Word;
udp_crc : Word;
end;
// Типы, необходимые для функционирования Winsock 2
u_char = Char;
u_shlort = Word;
u_int = Integer;
u_long = Longint;
SndB = packed record
s_b1, s_b2, s_b3, s_b4: u_char;
end;
SndW = packed record
s_w1, s_w2: u_shlort;
end;
in_addr = record
case integer of
0: (S_un_b: SndB);
1: (S_un_w: SndW);
2: (S_addr: u_long);
end;
TInAddr = in_addr;
Sockaddr_in = record
case Integer of
0: (sin_family: u_shlort;
sin_port: u_shlort;
sin_addr: TInAddr;
sin_zero: array[0..7] of Char);
1: (sa_family: u_shlort;
sa_data: array[0..13] of Char)
end;
TSockAddr = Sockaddr_in;
TSocket = u_int;
type
PWSAData = ^TWSAData;
WSAData = record
wVersion: Word;
wHighVersion: Word;
szSystemStatus: array[0..128] of Char; //Объявляем системный статус
szDescription: array[0..256] of Char; //Описание
iMaxSockets: Word;
lpVendorInfo: PChar;
iMaxUdpDg: Word;
end;
TWSAData = WSAData;
//Здесь определим функции winsock 2
function sendto(s: TSocket; var Buf; len, flags: Integer; var addrto: TSockAddr;
tolen: Integer): Integer; stdcall;
function socket(af, Struct, protocol: Integer): TSocket; stdcall;
function closesocket(s: TSocket): Integer; stdcall;
function setsockopt(s: TSocket; level, optname: Integer; optval: PChar;
optlen: Integer): Integer; stdcall;
function inet_addr(cp: PChar): u_long; stdcall; {PInAddr;} { TInAddr }
function htons(hostshlort: u_shlort): u_shlort; stdcall;
function WSAGetLastError: Integer; stdcall;
function WSAStartup(wVersionRequired: word; var WSData: TWSAData): Integer; stdcall;
function WSACleanup: Integer; stdcall;
const
AF_NTWRK = 2; // Константа сети: UDP, TCP, и т.д.
IP_HEADER = 2; // Объявляем заголовок IP пакета
DUMMY_UDP = 17; // Это объявление хедера UDP
RAW_SCK = 3; // Объявляем интерфейс сокета RAW пакета
DUMMY_RAW = 255; // raw IP пакет
DYMMY_IP = 0; // dummy [IP]
DUMMY_TCP = 6; // Объявляем интерфейс TCP
BAD_SOCKET = TSocket(NOT(0));
SOCKET_ERROR = -1;
var Form1: TForm1;
SrcIP,SrcPort,DestIP,DestPort, PacketBody: Variant;
implementation
const WinSocket = 'WS2_32.DLL';
function closesocket; external winsocket name 'closesocket';
function socket; external winsocket name 'socket';
function sendto; external winsocket name 'sendto';
function setsockopt; external winsocket name 'setsockopt';
function inet_addr; external winsocket name 'inet_addr';
function htons; external winsocket name 'htons';
function WSAGetLastError; external winsocket name 'WSAGetLastError';
function WSAStartup; external winsocket name 'WSAStartup';
function WSACleanup; external winsocket name 'WSACleanup';
{$R *.dfm}
procedure FillVariables;
begin
SrcIP := Form1.SourceIP.Text;
SrcPort:= Form1.DestinPrt.Text;
DestIP := Form1.DestinIP.Text;
DestPort := Form1.DestinPrt.Text;
PacketBody := Form1.PcktData.Text;
end;
// ################################
// Проверяем целостность данных пакета
// #################################
function Checrcsum(Var Buffer; Size : integer) : Word;
type
TWordArray = Array[0..1] of Word;
var
CRC : LongWord;
i : Integer;
begin
CRC := 0;
i := 0;
While Size > 1 do begin
CRC := CRC + TWordArray(Buffer);
inc(i);
Size := Size - SizeOf(Word);
end;
if Size=1 then CRC := CRC + Byte(TWordArray(Buffer));
CRC := (CRC shr 16) + (CRC and $FFFF);
CRC := CRC + (CRC shr 16);
Result := Word(CRC);
end;
procedure MakeHdrs(
FromIP : String;
iFromPort : Word;
ToIP : String;
iToPort : Word;
StringMsg : String;
Var Buf : TPcktBuf;
Var remote : TSockAddr;
Var iTotalSize : Word
);
Var
shFromIP : LongWord;
shToIP : LongWord;
iIPVer : Word;
iIPSize : Word;
ipHdr : T_IP_Header;
udpHdr : T_UDP_Header;
iUdpSize : Word;
iUdpChecrcsumSize : Word;
crcsum : Word;
P_rt : ^Byte;
procedure IncP_rt(Value : Integer);
begin
P_rt := pointer(integer(P_rt) + Value);
end;
begin
// Выполняем преобразование IP адресов
shFromIP := inet_Addr(PChar(FromIP));
shToIP := inet_Addr(PChar(ToIP));
//Производим инициализацию заголовка пакета.
//
iTotalSize := sizeof(ipHdr) + sizeof(udpHdr) + length(StringMsg);
iIPVer := 4;
iIPSize := sizeof(ipHdr) div sizeof(LongWord);
//
// Версия IP протокола (старшие 4 бита) .
// Длина IP заголовка (нижние 4 бита).
//
ipHdr.ipver := (iIPVer shr 4) or iIPSize;
ipHdr.ipts := 0; // тип IP сервиса
ipHdr.iplength := htons(iTotalSize); // Длина пакета
ipHdr.ipID := 0; // Уникальный идентификатор пакета(по умолчанию равен 0)
ipHdr.ipoffst := 0; // Яйчейка смещения фрагмента
ipHdr.ipttl := 128; // Время жизни пакета(TTL)
ipHdr.iptype := $11; // Устанавливаем протокол($11 - UDP)
ipHdr.ipcrc := 0 ; // Checksum'а пакета
ipHdr.ipscrIP := shFromIP; // Адрес отпр-ля
ipHdr.ipdestIP := shToIP; // Адрес назначения пакета
//
// Выполняем инициализацию UDP пакета
//
iUdpSize := sizeof(udpHdr) + length(StringMsg);
udpHdr.src_portnumb := htons(iFromPort) ;
udpHdr.dst_portnumb := htons(iToPort) ;
udpHdr.udp_len := htons(iUdpSize) ;
udpHdr.udp_crc := 0 ;
//
// Построение псевдозаголовка UDP для подсчета контрольной суммы UDP .
iUdpChecrcsumSize := 0;
P_rt := @buf[0];
FillChar(Buf, SizeOf(Buf), 0);
Move(ipHdr.ipscrIP, P_rt^, SizeOf(ipHdr.ipscrIP));
IncP_rt(SizeOf(ipHdr.ipscrIP));
iUdpChecrcsumSize := iUdpChecrcsumSize + sizeof(ipHdr.ipscrIP);
Move(ipHdr.ipdestIP, P_rt^, SizeOf(ipHdr.ipdestIP));
IncP_rt(SizeOf(ipHdr.ipdestIP));
iUdpChecrcsumSize := iUdpChecrcsumSize + sizeof(ipHdr.ipdestIP);
IncP_rt(1);
Inc(iUdpChecrcsumSize);
Move(ipHdr.iptype, P_rt^, sizeof(ipHdr.iptype));
IncP_rt(sizeof(ipHdr.iptype));
iUdpChecrcsumSize := iUdpChecrcsumSize + sizeof(ipHdr.iptype);
Move(udpHdr.udp_len, P_rt^, sizeof(udpHdr.udp_len));
IncP_rt(sizeof(udpHdr.udp_len));
iUdpChecrcsumSize := iUdpChecrcsumSize + sizeof(udpHdr.udp_len);
move(udpHdr, P_rt^, sizeof(udpHdr));
IncP_rt(sizeof(udpHdr));
iUdpChecrcsumSize := iUdpChecrcsumSize + sizeof(udpHdr);
Move(StringMsg[1], P_rt^, Length(StringMsg));
IncP_rt(Length(StringMsg));
iUdpChecrcsumSize := iUdpChecrcsumSize + length(StringMsg);
crcsum := checrcsum(buf, iUdpChecrcsumSize);
udpHdr.udp_crc := crcsum;
// Теперь выполним построение заголовков пакетов IP и UDP
FillChar(Buf, SizeOf(Buf), 0);
P_rt := @Buf[0];
Move(ipHdr, P_rt^, SizeOf(ipHdr)); IncP_rt(SizeOf(ipHdr));
Move(udpHdr, P_rt^, SizeOf(udpHdr)); IncP_rt(SizeOf(udpHdr));
Move(StringMsg[1], P_rt^, length(StringMsg));
remote.sin_family := AF_NTWRK;
remote.sin_port := htons(iToPort);
remote.sin_addr.s_addr := shToIP;
end;
procedure TForm1.SendIt;
Var
shll : TSocket;
bOpt : Integer;
ret : Integer; //адрес возврата
Buf : TPcktBuf; //буфер
Remote : TSockAddr;
iTotalSize : Word; //размер
wsdata : TWSAdata;
begin
// Запускаем Winsock 2
ret := WSAStartup($0002, wsdata);
if ret<>0 then begin
memo1.lines.add('Ошибка при запуске WSA');
exit;
end;
with memo1.lines do begin
add('Запуск WSA:');
add('Описание: '+wsData.szDescription);
add('Состояние: '+wsData.szSystemStatus);
end;
try
// Создание сокета
shll := Socket(AF_NTWRK, RAW_SCK, DUMMY_UDP);
if (shll = BAD_SOCKET) then begin
memo1.lines.add('Отправка сокета окончилась неудачей:( '+IntToStr(WSAGetLastError));
exit;
end;
// Включаем опцию заголовков
bOpt := 1;
ret := SetSockOpt(shll, DYMMY_IP, IP_HEADER, @bOpt, SizeOf(bOpt));
if ret = SOCKET_ERROR then begin
Memo1.lines.add('Установка опции заголовка обломилась:( '+IntToStr(WSAGetLastError));
exit;
end;
// Выполняем построение пакета
MakeHdrs(SrcIP, SrcPort,
DestIP, DestPort,
PacketBody,
Buf, Remote, iTotalSize );
// Посылаем пакет=)
ret := SendTo(shll, buf, iTotalSize, 0, Remote, SizeOf(Remote));
if ret = SOCKET_ERROR then
Memo1.Lines.Add('Отправка не удалась: '+IntToStr(WSAGetLastError))
else
Memo1.Lines.Add('Отправлено '+IntToStr(ret)+' байт.');
// Закрываем сокет
CloseSocket(shll);
finally
// Прекращаем работу Winsock 2
WSACleanup;
end;
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
memo1.Clear;
FillVariables;
SendIt;
end;
end.