#include "stdafx.h" #include "proxy.h" #include
#ifdef _debug # define new debug_new # undef this_filestatic char this_file [] = __file __; # ENDIF
/
#define http "http://" #define ftp "ftp: //" #define proxyport 5001 // proxy port #define bufsize 10240 // buffer size
CWINAPPPP;
Using namespace std;
Uint ProxyToServer (LPVOID PPARAM); Uint UserToproxythread (Void * PParam);
struct SocketPair {SOCKET user_proxy; // socket: PROXY service machine to the local machine SOCKET proxy_server; // socket: PROXY service unit to the remote host BOOL IsUser_ProxyClosed; // PROXY local machine to the service state machine BOOL IsProxy_ServerClosed; // PROXY machine to service Remote host status};
Struct ProxyParam {char address [256]; // Remote Host Address Handle User_SVrok; // Proxy server to the connection status of the remote host socketpair * ppair; // Maintain a set of socket pointer INT port; // Used to connect the remote host Port}; // This structure is used to exchange information from the remote host.
Socket Glisten_Socket; // Socket used to listen.
INT StartServer () // Start service {wsadata wsadata; sockaddr_in local; socket listen_socket;
IF (: wsastartup (0x202, & wsadata)! = 0) {Printf ("/ NERROR IN Startup session./n" );wsacleanup(); Return -1;
Local.sin_Family = AF_INET; local.sin_addr.s_addr = incdr_any; local.sin_port = htons (proxyport);
Listen_Socket = Socket (AF_INET, SOCK_STREAM, 0); if (listen_socket == invalid_socket) {Printf ("/ NERROR IN New A socket."); wsacleanup (); return -2;}
IF (:: bind (sockaddr *) & local, sizeof (local))! = 0) {Printf ("/ n error in binding socket."); wsacleanup (); return -3;};
IF (:: Listen_Socket, 5)! = 0) {Printf ("/ N Error In Listen."); wsacleanup (); Return-4;} glisten_socket = listen_socket; AFXBEGINTHREAD (UserToproxythread, null); // Startup Listening to returnit 1;}
INT CloseServer () // Turn off the service {closeSocket; wsacleanup (); Return 1;} // Analyze the received characters to get the remote host address INTGETDRESSANDPORT (Char * STR, CHAR * Address, INT * port) { Char BUF [Bufsize], Command [512], Proto [128], * P; INT J; SSCANF (STR, "% S% S% S% S", Command, BUF, Proto; P = strstr (buf, http) ; // httpif (p) {p = strlen (http); for (int i = 0; i STRCPY (Address, p); p = str, ftp); for (j = 0; j
// get the local data destined for a remote host UINT UserToProxyThread (void * pParam) {char Buffer [BUFSIZE]; int Len; sockaddr_in from; SOCKET msg_socket; int fromlen, retval; SocketPair SPair; ProxyParam ProxyP; CWinThread * pChildThread; fromlen = sizeof (from); msg_socket = accept (gListen_Socket, (struct sockaddr *) & from, & fromlen); AfxBeginThread (UserToProxyThread, pParam); // start another listener .if (msg_socket == INVALID_SOCKET) {printf ( "/ NERROR IN Accept "); return -5;} // read the first line of data of the customer Spair.isuser_proxyclosed = false; spair.isproxy_serverclosed = true; spair.user_proxy = msg_socket; RETVAL = RECV (spair.user_proxy, buffer, sizeof (buffer), 0); if (RetVal == Socket_ERROR) {Printf ("/ Nerror Recv"); if (spair.isuser_proxyclosed == false) {CloseSocket (Spair.user_Proxy ); SPair.IsUser_ProxyClosed = TRUE;}} if (retval == 0) {printf ( "Client Close connection / n"); if (SPair.IsUser_ProxyClosed == FALSE) {closesocket (SPair.user_proxy); SPair.IsUser_ProxyClosed = True;}} len = retval; #ifdef _debug Buffer [len] = 0; Printf ("/ n Received% D Bytes, DATA [% s] from client / n", retval, buffer; # endif // spair.isuser_proxyclosed = false; spair.isproxy_serverclosed = true; spair .user_proxy = msg_socket; Proxyp.ppair = & spair; proxyp.user_svrok = CreateEvent (Null, true, false, null); GetDressandport (Buffer, Proxyp.address, & Proxyp.Port); PCHildThread = AFXBEGINTHREAD (PROXYTOSERVER, (LPVOID) & proxyp); :: waitforsingleObject (Proxyp.user_svrok, 60000); // Waiting for Joint :: CloseHandle (Proxyp.user_svrok); While (spair.isproxy_serverclosed == false&is == false) {RetVal = send (spair.proxy_server, buffer, len, 0); if (retval == socket_error) {printf ("/ n send () failed: error% d / n ", WSAGetLastError ()); if (SPair.IsProxy_ServerClosed == FALSE) {closesocket (SPair.proxy_server); SPair.IsProxy_ServerClosed = TRUE;} continue;} retval = recv (SPair.user_proxy, Buffer, sizeof (Buffer), 0); if (retval == SOCKET_ERROR) {printf ( "/ nError Recv"); if (SPair.IsUser_ProxyClosed == FALSE) {closesocket (SPair.user_proxy); SPair.IsUser_ProxyClosed = TRUE;} continue;} if (retval == 0 ) {printf ( "Client Close connection / n"); if (SPair.IsUser_ProxyClosed == FALSE) {closesocket (SPair.user_proxy); SPair.IsUser_ProxyClosed = TRUE;} break;} Len = retval; #ifdef _DEBUGBuffer [Len] = 0; Printf ("/ n Received% D Bytes, DATA [% s] from client / n", retval, buffer; # endif} // end while if (SPair.IsProxy_ServerClosed == FALSE) {closesocket (SPair.proxy_server); SPair.IsProxy_ServerClosed = TRUE;} if (SPair.IsUser_ProxyClosed == FALSE) {closesocket (SPair.user_proxy); SPair.IsUser_ProxyClosed = TRUE;} :: WaitForSingleObject (pChildThread-> m_hThread, 20000); // Should check the return valuereturn 0;} // reading the remote host data, and sent to the local client UINT ProxyToServer (LPVOID pParam) {ProxyParam * pPar = (ProxyParam *) pParam ; char Buffer [BUFSIZE]; char * server_name = "localhost"; unsigned short port; int retval, Len; unsigned int addr; int socket_type; struct sockaddr_in server; struct hostent * hp; SOCKET conn_socket; Socket_type = SOCK_STREAM; Server_Name = PPAR-> Address; Port = PPAR-> Port; IF (isalpha (server_name [0])) {/ * server address is a name * / hp = gethostByname (server_name);} else {/ * convert nnn.nnnnn address to a usable one * / addr = inet_addr (server_name); HP = gethostbyaddr ((char *) & addr, 4, af_inet);} if (hp == null) {fprintf (stderr, "client: cannot resolve address [% s]: error% d / n", server_name, wsagetlasterror )) ;: setEvent (ppar-> user_svrok; return 0;} //// copy the resolved information inteo the sockaddr_in structure // Memset (Server, 0, SIZEOF (Server)); Memcpy (& (Server.sin_ADDR), HP-> h_addr, hp-> h_length); Server.sin_Family = HP-> h_addrtype; server.sin_port = htons (port); conn_socket = socket (AF_INET, SOCKET_TYPE, 0); / * Open a socket * / if (conn_socket <0) {fprintf (stderr, "Client: Error Opening Socket: Error% D / N ", wsagetlasterror ()); ppar-> ppair-> isproxy_serverclosed = true; :: set-> user_svrok; return -1;} # ifdef _debugprintf (" Client connection to:% s / n ", hp-> h_name); # endifif (Conn_Socket, (Struct SockAddr *) & Server, SIZEOF (Server)) == Socket_ERROR) {fPrintf (stderr," connect () failed:% d / n ", Wsagetlasterror )); ppar-> ppair-> isproxy_serverclosed = true; :: set-> user_svrok; return -1;} PPAR-> ppair-> proxy_server = conn_socket; ppar-> ppair-> isproxy_serverclosed = false; :: SetEvent (ppar-> user_svrok; // cook up a string to sendwhile (! Ppar-> ppair-> isproxy_serverclosed &&! Ppar-> ppair-> iSuser_proxyclosed) {RetVal = Recv (conn_soc) KET, Buffer, Sizeof (Buffer), 0); if (Retval == Socket_ERROR) {FPRINTF (stderr, "RECV () failed: error% d / n", wsagetlasterror ()); clossoSocket (conn_socket); PPAR-> pPair-> IsProxy_ServerClosed = TRUE; break;} Len = retval; if (retval == 0) {printf ( "Server closed connection / n"); closesocket (conn_socket); pPar-> pPair-> IsProxy_ServerClosed = TRUE; break; } Retval = send (ppar-> ppair-> user_proxy, buffer, len, 0); if (retval == socket_error) {fPrintf (stderr, "send () failed: error% d / n", wsagetlasterror (); CloseSocket (PPAR-> PPAIR-> User_Proxy); PPAR-> PPAIR-> iSuser_Proxyclosed = true; break;} #ifdef _debug buffer [len] = 0; printf ("received% D Bytes, Data [% s] from server / N ", retval, buffer); # endif} if (ppar-> ppair-> isproxy_serverclosed == false) {closesocket (ppar-> ppair-> proxy_server); ppar-> ppair-> isproxy_serverclosed = true;} if (PPAR- > PPAIR-> iSUser_Proxyclosed == false) {CloseSocket (PPAR-> PPAIR-> User_Proxy); PPAR-> PPAIR-> iSuser_Proxyclosed = true;} return 1;} int _tmain (int Argc, tchar * argv [], tchar * Envp []) {INT nretcode = 0; // Initialize Socketif (! AFXWININIT (: :: getcommandline (), :: getcommandline (), 0) {// Error handling CERR <<_t ("Fatal Error: MFC Initialization Failed) Return nretcode;}