基于visual c++之windows核心编程代码分析(59)实现网络简单代理编程

本文介绍了一种简易网络代理服务器的实现方法,并提供了一个具体的代码示例。该代理服务器能够帮助内部网络用户通过代理访问外部资源,同时具备基本的数据转发功能。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

  总得来说呢,就是一个网络信号的跳转,就是让网络请求信号通过第三方(代理)向你要访问的那个网站发请求,然后这个网站会认为是第三方向他请求的,然后去验证看是否合他的要求,当然信号 接收也一样,当你要接收信号时,会认为接收到的是第三方的网络信号,而不会去验证,你实际上去访问的这个网站的内容及地址!

通过代理服务器连接网络的优点   

(1)设置用户验证和记账功能,可按用户进行记账,没有登记的用户无权通过代理服务器访问Internet网。并对用户的访问时间、访问地点、信息流量进行统计。

  (2)对用户进行分级管理,设置不同用户的访问权限,对外界或内部的Internet地址进行过滤,设置不同的访问权限。  

 (3)增加缓冲器(Cache),提高访问速度,对经常访问的地址创建缓冲区,大大提高热门站点的访问效率。通常代理服务器都设置一个较大的硬盘缓冲区(可能高达几个GB或更大),当有外界的信息通过时,同时也将其保存到缓冲区中,当其他用户再访问相同的信息时,则直接由缓冲区中取出信息,传给用户,以提高访问速度。  

 (4)连接内网与Internet,充当防火墙(Firewall):因为所有内部网的用户通过代理服务器访问外界时,只映射为一个IP地址,所以外界不能直接访问到内部网;同时可以设置IP地址过滤,限制内部网对外部的访问权限。

 

下面我们来亲自实践一个简单的网络代理

 

 

#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <winsock2.h> 
#include <io.h>

#pragma comment(lib, "ws2_32.lib")

#define MAXSIZE                        20480

struct TransferSocket 
{
     SOCKET fd1;
     SOCKET fd2;
};


void ClientThread(LPVOID data);

int ConnectHost(int SocketSer, char* server, int port);


//************************************************************************************
VOID main(int argc, char* argv[])
{
	char ServerHost[256] = {0};
    int ClientPort=0, ServerPort=0;

    WSADATA wsadata;
    WSAStartup(MAKEWORD(1, 1), &wsadata);


    if (argc != 4)
	{
		 printf("example: Proxy.exe 8181 68.13.145.77 8181");
		 return;
	}

    ClientPort = atoi(argv[1]);
	strcpy(ServerHost, argv[2]);
    ServerPort = atoi(argv[3]);

	
                
     
    SOCKET SocketListen,SocketClient,SocketServer;
    struct sockaddr_in remote;
    int size;
    char buffer[1024];

    HANDLE hThread=NULL;
    TransferSocket sock;
    DWORD dwThreadID;

    if (ClientPort > 65535 || ClientPort < 1)
    {
           printf("Client connectPort invalid.\r\n");
           return;
    }

     if (ServerPort > 65535 || ServerPort < 1)
     {
           printf("Server connectPort invalid.\r\n");
           return;
     }
     
     memset(buffer,0,1024);

	 //----------

     SocketListen=socket(AF_INET,SOCK_STREAM,0);
     if(SocketListen<=0)
     {
           printf("Create socket error.\r\n");
           return;
     }
     
	 //-----------

     struct sockaddr_in srvaddr;
     int on=1;
    
     memset(&srvaddr, 0, sizeof(struct sockaddr));

     srvaddr.sin_port=htons(ClientPort);
     srvaddr.sin_family=AF_INET;
     srvaddr.sin_addr.s_addr=htonl(INADDR_ANY);
  
     setsockopt(SocketListen,SOL_SOCKET,SO_REUSEADDR, (char*)&on,sizeof(on)); 

     if(bind(SocketListen,(struct sockaddr *)&srvaddr,sizeof(struct sockaddr))<0)
     {
           printf("Listen socket bind error.\r\n");
           return;
     }

     if(listen(SocketListen,8)<0)
     {
           printf("Socket Listen error.\r\n");
           return;
     }

     
     size=sizeof(struct sockaddr);
     while(1)
     {
           printf("Waiting for Client ......\r\n");      
           if((SocketClient=accept(SocketListen,(struct sockaddr *)&remote,&size))<0)
           {
                 printf("Accept error.\r\n");
                 continue;
           }

           printf("Accept a Client from %s:%d ......\r\n",
           inet_ntoa(remote.sin_addr), ntohs(remote.sin_port));

		   SocketServer=socket(AF_INET,SOCK_STREAM,0);
           if(SocketServer <= 0)
		   {
			   printf("Create socket error.\r\n");
		       closesocket(SocketClient);
               return;
		   }
                      
           printf("Make a Connection to %s:%d ......\r\n",ServerHost,ServerPort);

           if(ConnectHost(SocketServer,ServerHost,ServerPort)==0)
           {
                 closesocket(SocketServer);
                 closesocket(SocketClient);
                 continue;
           }
           
           printf("Connect successed!\r\n");

           sock.fd1 = SocketClient;
           sock.fd2 = SocketServer;

           hThread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)ClientThread, (LPVOID)&sock, 0, &dwThreadID); 
           if(hThread == NULL) 
           {
                 TerminateThread(hThread, 0);
                 return;
           }

           Sleep(1000);
           printf("CreateThread successed!\r\n\n");
     }

     WSACleanup();

     return;
}

void ClientThread(LPVOID data)
{
     SOCKET fd1, fd2;
     TransferSocket *sock;
     struct timeval timeset;
     fd_set readfd,writefd;
     int result,i=0;
     char read_in1[MAXSIZE],send_out1[MAXSIZE];
     char read_in2[MAXSIZE],send_out2[MAXSIZE];
     int read1=0,totalread1=0,send1=0;
     int read2=0,totalread2=0,send2=0;
     int sendcount1,sendcount2;
     int maxfd;
     int structsize1,structsize2;
     char tmpbuf[100];

     sock = (TransferSocket *)data;
     fd1 = sock->fd1;
     fd2 = sock->fd2;

     memset(tmpbuf,0,100);

     structsize1=sizeof(struct sockaddr);
     structsize2=sizeof(struct sockaddr);
 
     maxfd=max(fd1,fd2)+1;
     memset(read_in1,0,MAXSIZE);
     memset(read_in2,0,MAXSIZE);
     memset(send_out1,0,MAXSIZE);
     memset(send_out2,0,MAXSIZE);
  
     timeset.tv_sec=1000;
     timeset.tv_usec=0;

     while(1)
     {
           FD_ZERO(&readfd);
           FD_ZERO(&writefd); 
       
           FD_SET((UINT)fd1, &readfd);
           FD_SET((UINT)fd1, &writefd);
           FD_SET((UINT)fd2, &writefd);
           FD_SET((UINT)fd2, &readfd);
       
           result=select(maxfd,&readfd,&writefd,NULL,×et);
           if((result<0) && (errno!=EINTR))
           {
                 printf("Select error.\r\n");
                 break;
           }
           else if(result==0)
           {
                 printf("Socket time out.\r\n");
                 break;
           }
           if(FD_ISSET(fd1, &readfd))
		   {
                 if(totalread1<MAXSIZE)
               {
                       read1=recv(fd1, read_in1, MAXSIZE-totalread1, 0); 
                       if((read1==SOCKET_ERROR) || (read1==0))
                       {
                             printf("Read client data error\r\n");
                             break;
                       }
                       memcpy(send_out1+totalread1,read_in1,read1);

                       totalread1+=read1;
                       memset(read_in1,0,MAXSIZE);
                 }
           }

           if(FD_ISSET(fd2, &writefd))
           {
                 int err=0;
                 sendcount1=0;
                 while(totalread1>0)
                 {
                       send1=send(fd2, send_out1+sendcount1, totalread1, 0);
                       if(send1==0)break;
                       if((send1<0) && (errno!=EINTR))
                       {
                             printf("Send to server error.\r\n");
                             err=1;
                             break;
                       }
                       
                       if((send1<0) && (errno==ENOSPC)) break;
					   
                       sendcount1+=send1;
                       totalread1-=send1; 

                 }
               
                 if(err==1) break;
                 if((totalread1>0) && (sendcount1>0))
                 {
                       memcpy(send_out1,send_out1+sendcount1,totalread1);
                       memset(send_out1+totalread1,0,MAXSIZE-totalread1);
                 }
                 else
                 memset(send_out1,0,MAXSIZE);
           } 
           
           if(FD_ISSET(fd2, &readfd))
           {
                 if(totalread2<MAXSIZE)
                 {
                       read2=recv(fd2,read_in2,MAXSIZE-totalread2, 0); 
                       if(read2==0)break;
                       if((read2<0) && (errno!=EINTR))
                       {
                             printf("Read server data error\r\n\r\n");
                             break;
                       }

                       memcpy(send_out2+totalread2,read_in2,read2);
					   
                 totalread2+=read2;
                 memset(read_in2,0,MAXSIZE);
                 }
		   }

           if(FD_ISSET(fd1, &writefd))
		   {
               int err2=0;
               sendcount2=0;
               while(totalread2>0)
               {
                     send2=send(fd1, send_out2+sendcount2, totalread2, 0);
                     if(send2==0)break;
                     if((send2<0) && (errno!=EINTR))
                     {
                           printf("Send to client  error.\r\n");
                             err2=1;
                           break;
                     }
                     if((send2<0) && (errno==ENOSPC)) break;
                     sendcount2+=send2;
                     totalread2-=send2; 
                     
               }
                 if(err2==1) break;
               if((totalread2>0) && (sendcount2 > 0))
                {
                       memcpy(send_out2, send_out2+sendcount2, totalread2);
                       memset(send_out2+totalread2, 0, MAXSIZE-totalread2);
                }
                else
                       memset(send_out2,0,MAXSIZE);
           } 

           Sleep(5);
     } 
  
     closesocket(fd1);
     closesocket(fd2);

     printf("\r\n Closed The Two Socket.\r\n"); 
}


int ConnectHost(int SocketSer,char* server,int port)
{
  struct sockaddr_in cliaddr;
  struct hostent *ServerHost;

  if(!(ServerHost=gethostbyname(server)))
  {
        printf("Gethostbyname(%s) error:%s\n",server,strerror(errno));
        return(0);
  }      
  
  memset(&cliaddr, 0, sizeof(struct sockaddr));
  cliaddr.sin_family=AF_INET;
  cliaddr.sin_port=htons(port);
  cliaddr.sin_addr=*((struct in_addr *)ServerHost->h_addr);
  
  if(connect(SocketSer,(struct sockaddr *)&cliaddr,sizeof(struct sockaddr))<0)
  {
        printf("Connect error.\r\n");
        return(0);
  }
  return 1;
}


 

转载于:https://www.cnblogs.com/new0801/archive/2012/01/24/6177766.html

你的程序加密过OD MD5值支持二次开发使用 防破解验证也可实现一机一码 VC++ 开发 STARTUPINFO startup; PROCESS_INFORMATION process; CString g_strCompanyName1 = ""; CString g_strCompanyName2 = ""; CString g_strCompanyName3 = ""; CString g_strCompanyName = "**"; BOOL CTaiShanApp::InitInstance() { AfxEnableControlContainer(); //#ifdef ZJH m_gMessageID = ::RegisterWindowMessage("WsSendMessageHqData"); CFileFind fnd; if(S_OK != ::CoInitialize (NULL)) return FALSE; // ReadDiskIDPartCwd(); // if(!FyRegister::IsValidUser()) // return FALSE; memset( &startup, 0, sizeof( startup ) ); startup.cb = sizeof( startup ); memset( &process, 0, sizeof( process ) ); if(fnd.FindFile ("WsSendMessageShare.exe")) { m_gbUseExe = true; } hAppMutex=::CreateMutex(NULL,TRUE,m_pszExeName); if(GetLastError() == ERROR_ALREADY_EXISTS) { CWnd *pPrevWnd = CWnd::GetDesktopWindow()->GetWindow(GW_CHILD); while(pPrevWnd) { if(::GetProp(pPrevWnd->GetSafeHwnd(),m_pszExeName)) { if(pPrevWnd->IsIconic()) pPrevWnd->ShowWindow(SW_RESTORE); pPrevWnd->SetForegroundWindow(); pPrevWnd->GetLastActivePopup()->SetForegroundWindow(); return false; } pPrevWnd = pPrevWnd->GetWindow(GW_HWNDNEXT); } return false; } //#endif #ifndef _NET_AUTHEN HMODULE hModule; hModule = LoadLibrary("ide21201.dll"); if (hModule==NULL) { AfxMessageBox("Can't find ide21201.dll"); return FALSE; } char *(WINAPI * GetIdeSerial)(); GetIdeSerial = (char *(WINAPI *)())GetProcAddress(hModule, "GetIdeSerial"); if (GetIdeSerial==NULL) { AfxMessageBox("Can't find GetIdeSerial in ide21201.dll"); return FALSE; } CString strSerialNumber;// = SERIAL_NUMBER; strSerialNumber = GetIdeSerial(); strSerialNumber.TrimLeft(" "); if (strSerialNumber.Compare(SERIAL_NUMBER)!=0) { AfxMessageBox("序列号错误"); return FALSE; } #else CDlgLogin dlgLogin; int nResponse = dlgLogin.DoModal(); if (nResponse!=1) return FALSE; #endif /* CDialogShowInformation dlg; dlg.DoModal();*/ int nResult; m_bAppAuthorized=TRUE; // Standard initialization // If you are not using these features and wish to reduce the size // of your final executable, you should remove from the following // the specific initialization routines you do not need. CTaiTestSplash *m_splash; BOOL SplashOpen=FALSE; m_splash = new CTaiTestSplash; SplashOpen=m_splash->Create(); if( SplashOpen ) m_splash->ShowWindow(SW_SHOW); DWORD Currenttime=GetTickCount(); BeginWaitCursor(); #ifdef TEST_USER1 t = CTime::GetCurrentTime(); CTime t2 = g_timeUseEnd; if(t >= t2) { // AfxMessageBox("试用期已过,若想继续使用,请购买正式版!",MB_OK | MB_ICONSTOP); return false; } else 以上为部分代码
光 盘 说 明 为了方便读者学习,本书附带了一张光盘,下面对光盘内容及使用方法进行简要的介绍。 1.光盘的运行环境 硬件环境:CPU的主频在200MHz以上、内存在64MB以上。 软件平台:操作系统Windows 98/Me/NT/2000/XP(推荐使用Windows 2000/XP),调试环境为Visual C++ 6.0及其以上版本(如果不做说明,则默认为Visual C++ 6.0)。 2.光盘的使用方法及注意事项 将本书的源代码拷入硬盘中,用Visual C++打开项目文件,即可编译运行。 3.光盘的主要内容 光盘中存放的是书中涉及的所有实例的源代码和经过编译后的应用程序。所有程序均经过测试,仅供读者学习时使用,不能用作其他商业用途。如果使用时遇到任何问题,请发Email至Fourwei@zj.com,我们将提供全面的解答。 4.光盘目录 (1)基本网络编程实例 Winsock实现网络聊天室【\chap1\ChatRoom(Winsock)】 CSocket实现聊天室【\chap1\ChatRoom(Csocket)】 (2)本地计算机网络编程实例 获取计算机的名称和IP地址【\chap2\Local】 获取计算机的子网掩码【\chap2\ Local】 获取计算机的DNS设置【\chap2\ Local】 获取计算机的网卡地址【\chap2\ Local】 获取计算机安装的协议【\chap2\ Local】 获取计算机提供的服务【\chap2\ Local】 获取计算机的所有网络资源【\chap2\ Local】 修改本地计算机的所有网络设置【\chap2\ Local】 获取计算机TCP/IP协议的所有信息【\chap2\ Local】 (3)局域网网络通信编程实例 获取网上邻居【\chap3\Neighbor】 lIP地址和计算机名之间的转换【\chap3\Neighbor】 l映射网络驱动器【\chap3\Neighbor】 l消息发送程序Net Send【\chap3\Neighbor】 l获取局域网内其他计算机的信息【\chap3\ NeighborInfo】 (4)IE编程实例 简单的浏览器的实现【\chap4\MyBrowser】 删除IE相关历史记录【\chap4\DelHistory】 将应用程序加入到IE工具栏【\chap4\AddToToolBar】 超级链接的实现【\chap4\HyperLink】 禁止IE的弹出窗口【\chap4\StopPopup】 禁止浏览某些网站【\chap4\StopTravel】 IE收藏夹【\chap4\ MyBrowser】 创建桌面快捷方式和活动桌面【\chap4\ShortCut】 (5)基本网络编程实例 点对点文件传输【\chap5\Transfer】 大型文件传输【\chap5\Transfer】 端口扫描程序【\chap5\ MyPortScanner】 Finger编程【\chap5\MyFinger】 Sniff编程【\chap5\MySniff】 Internet文件下载【\chap5\ InternetDownload】 (6)网络通信协议编程 FTP协议【\chap6\FTP】 Email协议【\chap6\Email】 ICMP协议【\chap6\ICMP】 RAS协议【\chap6\RAS】 TAPI协议【\chap6\TAPI】 Telnet协议【\chap6\Telnet】 HTTP协议 【\chap6\HTTP】 (7)Modem /串口通信编程 Modem编程【\chap7\Modem】 MSCOMM控件编程【\chap7\MSCOMM】 串口通信API编程【\chap7\MySerialCom】 (8)代理服务器编程实例 Socks 5协议编程【\chap8\Socks5】 HTTP代理服务器【\chap8\HTTP代理服务】 (9)高级网络通信编程实例 串口通信编程实例【\chap9\SerialPort】 网络流量监控【\chap9\NetTraffic】 网站下载【\chap9\ Snag】 网络五子棋系统【\chap9\FiveChess】 语音聊天【\chap9\ ChatRoom】 远程监控【\chap9\RemoteControl】 赠送实例 类似网络蚂蚁的断点续传程序【\Appendix\NetAnts】 网络多播程序【\Appendix\BroadCast】 界面美观的文字聊天程序【\Appendix\Chat】 语音电话【\Appendix\PhoneCall】
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值