Код:
program dproxy;
{$APPTYPE CONSOLE}
uses
windows,
WinSock,
StrUtils,
SysUtils,
uutil in 'uutil.pas';
const
pcount = 32;
var
wsaData : TWSADATA;
mainsock : TSocket;
client : TSOCKADDR;
csock : TSocket;
addr : SOCKADDR_IN;
Size : integer;
bol : boolean;
i : integer;
a_exit : array of boolean;
a_sock : array of TClientEx;
a_hndl : array of THandle;
function SocksHandlerTreadProc(pParam:pointer):DWORD; stdcall;
var
s1 : TSocket;
j : integer;
i : integer;
loop : integer;
bol : boolean;
buf_1: AnsiString;
buf : AnsiString;
buf_len : integer;
p : integer;
p2 : integer;
p3 : integer;
z_s : string;
recv_result : integer;
DataType : TDataType;
Host_str : string;
Host_host : string;
Host_port : string;
zapros_str : string;
url : string;
remHost : u_long;
RemPort : u_short;
sa : TSockaddrin;
lpMsgBuf : array[0..255] of Char;
name : TSockaddr;
begin
j := integer(pParam);
WHILE TRUE DO
BEGIN
while a_sock[j].Socket=0 do sleep(40);
i := sizeof(name);
getpeername(a_sock[j].Socket, name, i);
a_sock[j].client := LongToIp(name.sin_addr.S_addr);
z_s := #13#10;
loop := 0;
bol := True;
buf_1 := '';
buf := '';
buf_len := 1024;
DataType := dtGET;
while loop=0 do
begin
inc(loop);
while bol do
begin
setlength(buf_1,buf_len);
recv_result := recv(a_sock[j].Socket,buf_1[1],buf_len,0);
if recv_result>0 then setlength(buf_1,recv_result)
else break;
buf := buf + buf_1;
p := pos(z_s+z_s,buf);
if p<>0 then
begin
bol := False;
break;
end;
end;
if bol then break;
buf_1 := lowercase(copy(buf,1,4));
if buf_1<>'get ' then
if buf_1='post' then DataType := dtPOST
else if buf_1='head' then DataType := dtHEAD
else break;
p := pos(z_s,buf);
zapros_str := copy(buf,1,p-1);
delete(buf,1,p+1);
p := posex(#32,zapros_str);
p3 := p;
p2 := posex(#32,zapros_str,p+1);
url := copy(zapros_str,p+1,p2-p-1);
delete(zapros_str,p,p2-p+1);
delete(url,1,7);
p := pos('/',url);
host_str := copy(url,1,p-1);
delete(url,1,p-1);
p := pos(':',host_str);
if p=0 then
begin
host_port := '80';
host_host := host_str;
end
else
begin
host_host := copy(host_str,1,p-1);
host_port := copy(host_str,p+1,length(host_str));
end;
insert(#32+url+#32,zapros_str,p3);
buf := zapros_str + z_s + buf;
remHost := HostToLong(host_host);
RemPort := strtoint(host_port);
writeln(a_sock[j].client + ' ' + zapros_str);
s1 := socket(AF_INET, SOCK_STREAM,0);
FillChar(sa,sizeof(sa),0);
sa.sin_addr.S_addr := remHost;
sa.sin_family := af_inet;
sa.sin_port := htons(80);
if connect(s1,sa,sizeof(sa))<>SOCKET_ERROR then
begin
send(s1,buf[1],length(buf),0);
bol := True;
while bol do
begin
setlength(buf_1,buf_len);
recv_result := recv(s1,buf_1[1],buf_len,0);
if recv_result>0 then
begin
setlength(buf_1,recv_result);
send(a_sock[j].Socket,buf_1[1],length(buf_1),0);
end
else break;
end;
end;
shutdown(s1, SD_BOTH);
closesocket(s1);
end;
shutdown(a_sock[j].Socket, SD_BOTH);
closesocket(a_sock[j].Socket);
a_sock[j].Socket := 0;
END;
result := 0;
end;
begin
WSAStartup(MAKEWORD(2,0), wsaData);
mainsock := socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
addr.sin_family := AF_INET;
addr.sin_port := htons(8080);
addr.sin_addr.s_addr := INADDR_ANY;
Size := SizeOf(Client);
if (Bind(mainsock,addr,SizeOf(addr))=0) and (Listen(mainsock,$FF)=0) then
begin
setlength(a_exit,pcount);
setlength(a_sock,pcount);
setlength(a_hndl,pcount);
for i:=0 to pcount-1 do
begin
a_exit[i] := False;
a_sock[i].Socket := 0;
fillchar(a_sock[i].Client,buf1len,0);
CreateThread(nil,0,@SocksHandlerTreadProc,pointer(i),0,a_hndl[i]);
end;
while true do
begin
csock := accept(mainsock, @Client, @Size);
bol := True;
for i:=0 to pcount-1 do
if a_sock[i].Socket=0 then
begin
bol := False;
a_sock[i].Socket := csock;
// move(inet_ntoa(Client.sin_addr),a_sock[i].Client,buf1len);
break;
end;
if bol then
begin
shutdown(csock, SD_BOTH);
closesocket(csock);
end;
end;
end;
readln;
end.
|