вот не плохой socks server на Delphi: PHP: unit SocksServer; interface uses Windows,Winsock; var wsaData : TWSADATA; proxy_port:Integer; l_sock : TSocket; sock4 : SOCKADDR_IN; Client : TSockAddr; h1 : THandle; type TSOCKS4_REQUEST=record ucVersion : byte; ucCommand : byte; wDestPort : word; dwDestIp : dword; end; type TSOCKS5_REQUEST=record ucVersion : byte; ucCommand : byte; ucRzv : byte; ucAtyp : byte; dwDestIp : dword; wDestPort : word; end; procedure StartSocks; implementation procedure FlushRecvBufferUntil(s:TSOCKET;condition:Char); var iReceiveRes : integer; cDummy : char; begin repeat iReceiveRes := recv(s, cDummy, sizeof(cDummy), 0); until NOT ((iReceiveRes<>SOCKET_ERROR) and (iReceiveRes<>0) and (cDummy<>condition)); end; procedure SocksHandlerTreadProc(pParam:pointer); stdcall; var s : TSocket; tunnelSock : TSocket; iConnectResult : integer; iReceiveRes : integer; iSocketsSet : integer; socks4Request : TSOCKS4_REQUEST; socks4Response : TSOCKS4_REQUEST; socks5Request : TSOCKS5_REQUEST; socks5Response : TSOCKS5_REQUEST; remoteAddr : SOCKADDR_IN; fds_read : TFDset;//fd_set; tv : TTimeval; cSocksVersion : byte; nMethods : byte; Mbuffer : array[0..255] of byte; iSelectResult : integer; loop : integer; ulVal : u_long; swapBuffer : array[0..4096*16-1] of char; iRecvResult : integer; begin s := TSOCKET(pParam); tunnelSock := 0; loop := 0; while loop=0 do begin inc(loop); iConnectResult := 0; iReceiveRes := 0; iSocketsSet := 0; FD_ZERO(fds_read); FD_SET(s, fds_read); tv.tv_sec := 30; cSocksVersion := 0; iSelectResult := select(0, @fds_read, nil, nil, @tv); if (iSelectResult=SOCKET_ERROR) or (not iSelectResult>0) then break; ulVal := 0; ioctlsocket(s, FIONBIO , ulVal); iReceiveRes := recv(s, cSocksVersion, 1, MSG_PEEK); if (cSocksVersion=4) then //Socks 4 begin iReceiveRes := recv(s, socks4Request, sizeof(socks4Request), 0); if iReceiveRes=SOCKET_ERROR then break; ulVal := 1; ioctlsocket(s, FIONBIO , ulVal); FlushRecvBufferUntil(s, #0); if socks4Request.ucCommand = 1 then begin ulVal := 0; ioctlsocket(s, FIONBIO, ulVal); remoteAddr.sin_family := AF_INET; move(socks4Request.dwDestIp,remoteAddr.sin_addr,si zeof(remoteAddr.sin_addr)); remoteAddr.sin_port := socks4Request.wDestPort; tunnelSock := socket(AF_INET, SOCK_STREAM, 0); iConnectResult := connect(tunnelSock, remoteAddr, sizeof(remoteAddr)); if (iConnectResult<>SOCKET_ERROR) then begin // 1111111111 socks4Response.ucCommand := 90; socks4Response.ucVersion := 0; send(s, socks4Response, sizeof(socks4Response), 0); end else break; end else break; end; if (cSocksVersion=5) then //Socks 5 begin iReceiveRes := recv(s,nMethods,1,0); if iReceiveRes=SOCKET_ERROR then break; recv(s,Mbuffer,nMethods,0); Mbuffer[0]:=5; Mbuffer[1]:=0; send(s,Mbuffer,2,0); recv(s, socks5Request, sizeof(socks5Request), 0); if iReceiveRes=SOCKET_ERROR then break; ulVal := 1; ioctlsocket(s, FIONBIO , ulVal); FlushRecvBufferUntil(s, #0); if socks5Request.ucCommand = 1 then begin ulVal := 0; ioctlsocket(s, FIONBIO, ulVal); remoteAddr.sin_family := AF_INET; move(socks5Request.dwDestIp,remoteAddr.sin_addr,si zeof(remoteAddr.sin_addr)); remoteAddr.sin_port := socks5Request.wDestPort; tunnelSock := socket(AF_INET, SOCK_STREAM, 0); iConnectResult := connect(tunnelSock, remoteAddr, sizeof(remoteAddr)); if (iConnectResult<>SOCKET_ERROR) then begin socks5Response.ucCommand := 90; socks5Response.ucVersion := 0; send(s, socks5Response, sizeof(socks5Response), 0); end else break; end else break; end; ulVal := 0; ioctlsocket(tunnelSock, FIONBIO, ulVal); ioctlsocket(s, FIONBIO, ulVal); fillchar(swapBuffer,sizeof(swapBuffer),0); tv.tv_sec := 2; while true do begin sleep(50); FD_ZERO(fds_read); FD_SET(s, fds_read); FD_SET(tunnelSock, fds_read); iSocketsSet := select(0, @fds_read, nil, nil, @tv); //if (iSocketsSet == SOCKET_ERROR) _leave; if iSocketsSet > 0 then begin if FD_ISSET(s, fds_read) then begin iRecvResult := recv(s, swapBuffer, sizeof(swapBuffer), MSG_PEEK); if (iRecvResult=0) then break else iRecvResult := recv(s, swapBuffer, sizeof(swapBuffer), 0); if (iRecvResult <> SOCKET_ERROR) and (iRecvResult > 0) then send(tunnelSock, swapBuffer, iRecvResult, 0) else BREAK; end; if (FD_ISSET(tunnelSock, fds_read)) then begin iRecvResult := recv(tunnelSock, swapBuffer, sizeof(swapBuffer), MSG_PEEK); if iRecvResult = 0 then break else iRecvResult := recv(tunnelSock, swapBuffer, sizeof(swapBuffer), 0); if (iRecvResult <> SOCKET_ERROR) and (iRecvResult > 0) then send(s, swapBuffer, iRecvResult, 0) else break; end; end; end; end; closesocket(s); closesocket(tunnelSock); end; procedure StartSocks; var size:Integer; begin proxy_port := 1234; WSAStartup(MAKEWORD(2,0), wsaData); l_sock := socket(AF_INET, SOCK_STREAM, IPPROTO_TCP); sock4.sin_family := AF_INET; sock4.sin_port := htons(proxy_port); sock4.sin_addr.s_addr := INADDR_ANY; Size := SizeOf(Client); if (Bind(l_sock,sock4,SizeOf(sock4))=0) and (Listen(l_sock,$FF)=0) then while true do begin sleep(50); CreateThread(nil,0,@SocksHandlerTreadProc,Pointer( accept(l_sock, @Client, @Size)),0,h1); end; end; end.