使用相同的套接字从服务器获取响应? [英] Get response from server using the same socket?

查看:22
本文介绍了使用相同的套接字从服务器获取响应?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在编写一个带有客户端和服务器的小型应用程序 - 客户端发送问题,服务器回答.

I'm writing a small application with a client and a server - the client sends a question and the server answers.

我设法完成了第一部分 - 服务器从客户端获取问题,做一些工作并发回答案.我就是不知道如何告诉客户端等待服务器的响应.

I managed to do the first part - the server gets the question from the client, do some work and sends back an answer. I just can't figure out how to tell the client to wait for a response from the server.

这是我的客户端代码:

char* ipAddress = (char*)malloc(15);
wcstombs(ipAddress, (TCHAR*)argv[1], 15);
DWORD port = wcstod(argv[2], _T('\0'));
DWORD numOfThreads = wcstod(argv[3], _T('\0;'));
DWORD method = wcstod(argv[4], _T('\0;'));

//initialize windows sockets service
WSADATA wsaData;
int iResult = WSAStartup(MAKEWORD(2,2), &wsaData);
assert(iResult==NO_ERROR);

//prepare server address
sockaddr_in server_addr;
server_addr.sin_family = AF_INET;
server_addr.sin_addr.s_addr = inet_addr(ipAddress);
server_addr.sin_port = htons(port);

//create socket
SOCKET hClientSocket= socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
assert(hClientSocket!=INVALID_SOCKET);

//connect to server
int nRes=connect(hClientSocket, (SOCKADDR*)&server_addr, sizeof(server_addr));
assert(nRes!=SOCKET_ERROR);

char* buf = "GET /count.htm HTTP/1.1\r\nHost: 127.0.0.1:666\r\nAccept: text/html,application/xhtml+xml\r\nAccept-Language: en-us\r\nAccept-Encoding: gzip, deflate\r\nUser-Agent: Mozilla/5.0\r\n\r\n";

int nBytesToSend= strlen(buf);
int iPos=0;

while(nBytesToSend)
{
    int nSent=send(hClientSocket,buf,nBytesToSend,0);
    assert(nSent!=SOCKET_ERROR);

    nBytesToSend-=nSent;
    iPos+=nSent;
}

closesocket(hClientSocket);

int nLen = sizeof(server_addr);
SOCKET hRecvSocket=accept(hClientSocket,(SOCKADDR*)&server_addr, &nLen);
assert(hRecvSocket!=INVALID_SOCKET);

//prepare buffer for incoming data
char serverBuff[256];
int nLeft=sizeof(serverBuff);
iPos=0;

do //loop till there are no more data
{
    int nNumBytes=recv(hRecvSocket,serverBuff+iPos,nLeft,0);

    //check if cleint closed connection
    if(!nNumBytes)
        break;

    assert(nNumBytes!=SOCKET_ERROR);

    //update free space and pointer to next byte
    nLeft-=nNumBytes;
    iPos+=nNumBytes;

}while(1);

SOCKET hRecvSocket=accept(hClientSocket,(SOCKADDR*)&ser​​ver_addr, &nLen); 行之后的断言失败.

推荐答案

发送"循环后的 closesocket 和 accept 调用 - 删除这些调用.accept 用于侦听传入连接的服务器,而不是用于已经连接的客户端.

The closesocket and accept call after your "send" loop - remove those calls. accept is for servers listening for incoming connections, not for clients that are already connected.

在您的 send() 循环完成后,直接进入您的 recv() 循环.这应该可以解决您当前的问题:

After your send() loop completes, go straight into your recv() loop. That should solve your immediate problem:

此外,您的发送循环忘记在缓冲区上引用 iPos,就像我认为您打算这样做的那样.这就是你想要的:

Also, your send loop is forgetting to referenece iPos on the buffer like I think you intended to. This is what you wanted:

int nSent=send(hClientSocket,buf+iPos,nBytesToSend,0);

在网络编程中,由于网络条件超出您的控制,套接字将失败.所以对网络调用的断言"并不总是合适的.最好只是期待失败并准备好处理它.通常,关闭套接字和活动连接是处理大多数错误的方法.

In network programming, sockets will fail due to network conditions beyond your control. So "asserts" on network calls are not always appropriate. Better to just expect failure and be prepared to handle it. Typically, closing the socket and the active connection is the way to handle most errors.

这篇关于使用相同的套接字从服务器获取响应?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆