首页 文章

通过按Ctrl c关闭客户端时,服务器会连续处理上一个输入 . 为什么?

提问于
浏览
0

我在C中有一个客户端服务器程序 . 客户端在服务器收到命令时发送命令 .

但是如果通过按Ctrl C关闭客户端,服务器应用程序将处理先前的输入 .

示例 .

CLient.c                                Server.c
-------------------------------------------------
Enter COmmand: adf                     Command from client: adf

Enter COmmand: bbb                     Command from client: bbb

Enter Command: Ctrl+c                  Command from client: bb

我不明白为什么它处理以前的输入 .

以下是我的主要逻辑 .

main(){

    // bind, listen, accept is done.

            while(!done && !shutFlag){      //  Main server command Loop
        done = ReceiveRequestMessage(&request, connectedSock );
        if(done)
        {
            printf("Client closed the connection while recv() \n");
            printf("Listening for new client connection to establish... \n");
            connectedSock = accept(srvSock, (struct sockaddr *)&connectSAddr, &addrLen );
            printf("GetLastError: %d\n", GetLastError());
            done = FALSE;
            continue;

        }

        request.record[strlen(request.record)] ='\0';
        commandLen = strcspn(request.record, "\n\t");
        memcpy(sysCommand, request.record, commandLen);
        sysCommand[commandLen] = '\0';

        printf("Request recieved from client: %s -> Hex: %X\n\n", request.record, *(request.record));
    }

}

ReceiveRequestMessage 功能:

static BOOL ReceiveRequestMessage(REQUEST *pRequest, SOCKET sd){
    LONG32 nRemainRecv = 0, nRecv;
    LPBYTE pBuffer;
    BOOL disconnect = FALSE;

    nRemainRecv = RQ_HEADER_LEN;
    pBuffer = (LPBYTE) pRequest;
    while(nRemainRecv > 0 &&  !disconnect )
    {
        nRecv = recv (sd, pBuffer, nRemainRecv, 0); // Reading the 1st 4 bytes(length of record)to pRequest.
        if ( nRecv > 0 )
            printf("Bytes received in request.rqLen: %d\n", nRecv);
        else if ( nRecv == SOCKET_ERROR ){
            printf("Connection closed\n");
            return TRUE;
        }

        disconnect = (nRecv == 0);      // check connection is closed 
        nRemainRecv -= nRecv;
        pBuffer += nRecv;       
    }

    /*  Read the request record */
    nRemainRecv = pRequest->rqLen;
    /* Exclude buffer overflow */
    nRemainRecv = min(nRemainRecv, MAX_RQRS_LEN);

    pBuffer = (LPSTR)pRequest->record;  
    while(nRemainRecv > 0 && !disconnect)
    {
        nRecv = recv(sd, pBuffer, nRemainRecv, 0);
        if(nRecv > 0)
            printf("Bytes Received in request.record: %d\n", nRecv);
        else if(nRecv == SOCKET_ERROR){
            printf("Connection closed");
            return TRUE;
        }

        disconnect = (nRecv == 0);          // check connection is closed 
        nRemainRecv -= nRecv;
        pBuffer += nRecv;       
    }

    return disconnect;
}

如何在客户端中单击Ctrl C后消除最后一个打印语句?

手段:

每当客户端通过单击Ctrl C或以任何方式断开连接 . 如何通知服务器?

1 回答

  • 1
    • 函数 ReceiveRequestMessage() 返回其变量 disconnect 的值 .

    • 仅当 recv() 返回 0 时,该变量才设置为非零 .

    • recv() 的文档仅对远程端执行有序关闭(并且没有更多数据可用于接收)的情况承诺返回值 0 . 如果发生错误,它肯定会返回 -1 ,而不是 0 .

    • 假设客户端每次有效断开连接时都会执行有序关闭是不安全的,特别是假设它在被信号杀死时执行一个是不安全的,就像发送它时一样 . a Ctrl c .

    • 如果 ReceiveRequestMessage() 在不修改 pRequest 参数指向的对象的情况下返回 0 ,则调用者将看到先前发送的请求被重复 . 这就是你所观察到的 .

相关问题