c++ - 改进服务器以处理多个客户端

标签 c++ multithreading server

我正在尝试创建一个与 2 个客户端通信的服务器,每次 1 个。与一个客户端交谈后,服务器向两个客户端发送一条消息。 我找到了服务器的基本代码,并尝试将其升级以接受多个连接,我看到了两种方式:线程,或做套接字数组,但我无法理解。 有人可以向我解释如何使用线程并举例吗? 这是代码:

int main()
{
    WSADATA WsaDat;
    if (WSAStartup(MAKEWORD(2, 2), &WsaDat) != 0)
    {
        std::cout << "WSA Initialization failed!\r\n";
        WSACleanup();
        system("PAUSE");
        return 0;
    }

    SOCKET Socket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
    if (Socket == INVALID_SOCKET)
    {
        std::cout << "Socket creation failed.\r\n";
        WSACleanup();
        system("PAUSE");
        return 0;
    }

    SOCKADDR_IN serverInf;
    serverInf.sin_family = AF_INET;
    serverInf.sin_addr.s_addr = INADDR_ANY;
    serverInf.sin_port = htons(8888);

    if (bind(Socket, (SOCKADDR*)(&serverInf), sizeof(serverInf)) == SOCKET_ERROR)
    {
        std::cout << "Unable to bind socket!\r\n";
        WSACleanup();
        system("PAUSE");
        return 0;
    }

    listen(Socket, 1);

    SOCKET TempSock = SOCKET_ERROR;
    while (TempSock == SOCKET_ERROR)
    {
        std::cout << "Waiting for incoming connections...\r\n";
        TempSock = accept(Socket, NULL, NULL);
    }

    // If iMode!=0, non-blocking mode is enabled.
    u_long iMode = 1;
    ioctlsocket(Socket, FIONBIO, &iMode);

    Socket = TempSock;
    std::cout << "Client connected!\r\n\r\n";

    // Main loop
    for (;;)
    {
        char *szMessage = "Welcome to the server!\r\n";
        send(Socket, szMessage, strlen(szMessage), 0);

        int nError = WSAGetLastError();
        if (nError != WSAEWOULDBLOCK&&nError != 0)
        {
            std::cout << "Winsock error code: " << nError << "\r\n";
            std::cout << "Client disconnected!\r\n";

            // Shutdown our socket
            shutdown(Socket, SD_SEND);

            // Close our socket entirely
            closesocket(Socket);

            break;
        }

        Sleep(1000);
    }

    WSACleanup();
    system("PAUSE");
    return 0;
}

最佳答案

为此,您需要一个服务器套接字和一个客户端套接字数组,如下所示:

服务器:

ACCEPT:
int clientsock[2];
minsocks = 0;
numsocks = 2;
while(minsock < numsocks)
{
    clientsock[minsock] = accept(serversock,
    (struct sockaddr *) &clientaddr,
    (socklen_t *)&clientaddrlen);
    minsock++;
}


RECIEVE:


char message[6];
int data;
int limit = 6;
for(int i = 0; i < NUMSOCK; i++)
{
    int in = recv(clientsock[i], &message[index], limit, 0);
    if(in > 0)
    {
        index += in;
        limit -= in;
    }
    else if ( in == 0 )
        printf("Connection closed\n");
    else
        printf("recv failed: %d\n", WSAGetLastError());
}

这应该是您开始的良好开端。

线程 - C 版本

pthread_t sniffer_thread;
if( pthread_create( &sniffer_thread , NULL ,  connection_handler , (void*) new_sock) < 0)
    {
        perror("could not create thread");
        return 1;
    }

    //Now join the thread , so that we dont terminate before the thread
    //pthread_join( sniffer_thread , NULL);
    puts("Handler assigned");
 }

/*
 * This will handle connection for each client
 * */
void *connection_handler(void *socket_desc)
{
    //Get the socket descriptor
    int sock = *(int*)socket_desc;
    int read_size;
    char *message , client_message[2000];
    while(in != 0)
    {
        int in = recv(socket_desc, &client_message[index], limit, 0);
        if(in > 0)
        {
             index += in;
             limit -= in;
        }
        else
            printf("recv failed: %d\n", WSAGetLastError());   
    }
    //Free the socket pointer
    free(socket_desc);

    return 0;
}

关于c++ - 改进服务器以处理多个客户端,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27671372/

相关文章:

http - 我无法让子路由器正常工作

ruby-on-rails - 无法通过本地网络访问 Rails 服务器

c++ - 设置交叉口不起作用

c++ - 编译 boost 时 `threading=multi` 到底做了什么?

c++ - 通过引用或按值将共享指针作为参数传递给类

c++ - 单例和多线程

java swing线程回调

javascript - 如何从单独的日志文件检索数据

C++,操作二维数组

c++ - 在主体中调用方法与在构造函数列表中调用方法之间的区别