阻塞模式之多线程

本文介绍了一个简单的多客户端与服务器通信的例子,通过创建多个线程来处理客户端的连接请求,解决了阻塞模式下多客户端通信的问题。文中详细展示了如何初始化Winsock,创建并绑定监听套接字,以及如何接受客户端连接。

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

阻塞模式下的多线程编程

由于send recv等函数的阻塞,将会导致主程序一直在等待某个send或者recv调用结束,才会处理其他的事情,那么多客户端与服务器的通信将变得无法完成。此时将引用线程的方式来解决这一问题。

一个简单的多客户端与服务器通信

server.cpp

       SOCKET  sock_listen;

      SOCKET talk;

      WORD wVersionRequested;

      WSADATA wsaData;

      wVersionRequested= MAKEWORD( 2, 2 ); 

      int err = WSAStartup( wVersionRequested, &wsaData);

      if ( err != 0 )      

           return FALSE;        

      if ( LOBYTE( wsaData.wVersion ) != 2 || HIBYTE(wsaData.wVersion ) != 2 )

      {         

           WSACleanup();

           return FALSE;

      }

    if (INVALID_SOCKET == (sock_listen = socket(AF_INET,SOCK_STREAM, 0)))

      {

           printf("创建套接字失败\n");

           return FALSE;

      }

      printf(""创建套接字成功n");

 

      sockaddr_insrv_addr;

      memset(&srv_addr,0, sizeof(sockaddr));

      srv_addr.sin_family= AF_INET;

      srv_addr.sin_port= htons(6000);

      srv_addr.sin_addr.S_un.S_addr= htonl(INADDR_ANY);

      if (SOCKET_ERROR == bind(sock_listen, (sockaddr*)&srv_addr,sizeof(sockaddr)))

      {

           printf("监听套接字失败\n");

           return FALSE;

      }

      printf("监听套接字成功\n");

      listen(sock_listen,SOMAXCONN);    

      printf("监¨听成功......\n");

     while (1)

      {

           SOCKETtalk;

           sockaddr_inclient_addr;

           int len = sizeof(sockaddr);

           if (INVALID_SOCKET == (talk = accept(socket_listen, (sockaddr*)&client_addr, &len)))

           {

                 printf("接收套接字失败\n");

                 return;

           }    

          CreateThread(NULL, 0, RequstProc, (LPVOID)&talk 0, NULL);

//主程序在不断接受来自客户端的连接后,创建线程为每个客户端处理数据的传输。

}

补充一点:很疑惑的是我们定义的socket_listen的端口号是6000,那么每次连接accpet成功后的talk套接字是不是都是6000呢?答案是肯定的。具体可以查一下网络层

DWORD WINAPI RequstProc(LPVOID lpParameter)

{

         DWORD dwTid = GetCurrentThreadId();
         printf("SendFile(%d) is ok\n",dwTid);
        // 获得参数sokcet
       SOCKET ClientSendSocket = (SOCKET)lpParameter;

       //TODO:开始处理一些数据传输

}

 

另外可以使用多端口的方式,可以处理多客户并发从服务器传文件或者下载文件的问题。

在上述的requesteProc线程里面,我们可以再创建一个发送线程,和接收线程。

发送线程,在创建一个端口号7000,并一直在while(true)循环中accpet来自客户端的recv线程中的连接请求,同样客户端的recv线程也是创建一个7000的端口进行连接。等待连接结束之后,在此线程基础上,再次开辟线程用于处理数据的交换。

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值