TCP 阻塞模型下服务器和客户端的建立步骤

   TCP服务器建立的步骤:

    1.  调用socket建立TCP 套接字

    2.   调用bind将套接字跟本地地址绑定

    3.  调用listen建立监听

    4.  建立accept接受来自客户端的连接,返回新的连接套接字

    5.  在新的套接字上面,调用send/recv实现跟客户端的通信。

 

   

    

   TCP 客户端建立的步骤:

    1.  调用socket建立 TCP 套接字

    2.  调用connect实现跟服务器端的连接

    3.  调用send/recv实现跟服务器端的通信

 

 

   无论是在服务器端还是客户端,要关闭连接,调用closesocket即可。

 

 

   下面是练习的代码,当客户端成功连接到服务器端时,服务器端会打印出客户端的IP地址,会客户端发送过来的一段信息。

   

    服务器代码:

   

[cpp]  view plain copy
  1. //启动服务器,参数一socket类型,参数二服务器绑定的IP地址  
  2. bool  ServerClass::StartServer(int   Type,sockaddr_in  sin)  
  3. {  
  4.       SOCKET   listen_socket=   socket(AF_INET,Type,0);  
  5.   
  6.       if (listen_socket==INVALID_SOCKET )  
  7.       {  
  8.           cout<<"服务器创建 监听 socket失败"<<endl;  
  9.           return false;  
  10.       }  
  11.       else  
  12.       {  
  13.           cout<<"服务器创建 监听 socket成功"<<endl;  
  14.       }  
  15.   
  16.       int  iRet=bind(listen_socket,(sockaddr *)&sin,sizeof(sin));  
  17.       if (iRet!=0)  
  18.       {  
  19.           cout<<"服务器 bind绑定失败"<<endl;  
  20.           return  false;  
  21.       }   
  22.       else  
  23.       {  
  24.           cout<<"服务器 bind绑定成功"<<endl;  
  25.       }  
  26.   
  27.       iRet=listen(listen_socket,SOMAXCONN);  
  28.       if (iRet!=0)  
  29.       {  
  30.           cout<<"服务器 listen 失败"<<endl;  
  31.           return  false;  
  32.       }   
  33.       else  
  34.       {  
  35.           cout<<"服务器 listen 成功"<<endl;  
  36.       }  
  37.   
  38.       sockaddr_in   client_addr;  
  39.       SOCKET  client_socket;  
  40.       int     addr_len=sizeof(sockaddr_in);  
  41.   
  42.       char dataBuffer[MAX_PATH]={0};  
  43.       while(true)  
  44.       {  
  45.           cout<<"服务器进入循环接受连接"<<endl;  
  46.           client_socket=accept(listen_socket,(sockaddr *)&client_addr,&addr_len);  
  47.             
  48.           if (INVALID_SOCKET ==client_socket)  
  49.           {  
  50.               cout<<"accept接受连接失败"<<endl;  
  51.           }   
  52.           else  
  53.           {  
  54.               cout<<"accept接受连接成功,连接来自:"<<endl;  
  55.   
  56.               cout<<inet_ntoa(client_addr.sin_addr)<<endl;  
  57.   
  58.   
  59.               recv(client_socket,dataBuffer,MAX_PATH,0);  
  60.               cout<<"收到信息:"<<dataBuffer<<endl;  
  61.   
  62.               closesocket(client_socket);  
  63.           }  
  64.       }  
  65.   
  66.   
  67.   
  68. }  

 

 

   客户端代码:

  

[cpp]  view plain copy
  1. // 启动客户端  
  2. bool ClientClass::StartClient(int Type, sockaddr_in addr)  
  3. {  
  4.     SOCKET   socket_client=socket(AF_INET,Type,0);  
  5.   
  6.     if (socket_client==INVALID_SOCKET)  
  7.     {  
  8.         cout<<"客户端 创建 socket失败"<<endl;  
  9.         return false;  
  10.     }  
  11.     else  
  12.     {  
  13.         cout<<"客户端 创建 socket成功"<<endl;  
  14.     }  
  15.   
  16.     int  iRet=connect(socket_client,(sockaddr *)&addr,sizeof(sockaddr_in));  
  17.     if (iRet!=0)  
  18.     {  
  19.         cout<<"客户端 连接服务器 失败"<<endl;  
  20.         return  false;  
  21.     }   
  22.     else  
  23.     {  
  24.         cout<<"客户端连接服务器成功"<<endl;  
  25.     }  
  26.       
  27.     string strSend="Hello,I'm  TanGaoWen";  
  28.     send(socket_client,(char *)strSend.c_str(),strSend.length(),0);  
  29.   
  30.     //关闭socket连接  
  31.     closesocket(socket_client);  
  32.   
  33.   
  34.   
  35.   
  36.   
  37.   
  38.     return false;  
  39. }  

 

 

   服务器的I/O模型是阻塞型的,如果需要处理来自多个客户端的连接,那么就必须开多个线程,一般一个线程处理一个来自客户端的连接。这样会消耗大量的系统资源,所以一般不采用阻塞的套接字管理模型。而是采用非阻塞的I/O 模型。以前写socket的时候,都是傻乎乎的给每个连接开个线程,这样服务器端根本就不能够承受大量的客户端的连接,是不太现实的。

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值