试图了解阻塞套接字recv()。 阻止在客户端应用程序中实现的套接字并连接到服务器。 服务器应用程序中实现的IOCP非阻塞套接字。 客户端应用程序发送一些请求,服务器响应肯定或否定回复。有时服务器中的处理时间在同一毫秒内。一旦收到请求服务器应用程序立即响应。 处理大约400个请求/响应时,服务器应用程序以相同的毫秒响应,但客户端应用程序在5秒后收到。时间延迟。
我们尝试使用wireshark来分析延迟和观察的位置:
wireshark时间戳和客户端app log timestamp.i.e之间存在5秒的时差。客户端应用程序日志比wireshark时间戳晚5秒。
我们发现recv()从套接字缓冲区读取数据的平均时间为15毫秒。
问题是由于阻塞套接字? 这是代码;
int classA::ReceiveFullMessage(int sock)
{
int i=0, nRet;
unsigned short *tmplen, pktlen;
struct timeval tv;
int g_RcvLen = 0;
bool bIsTimeOut = false;
//HRESULT hr;
char *hbInvokeId;
char strMsg[2048];
memset(g_RcvBuf,0,MAXMESSAGEPACKET);
while (1)
{
// ***
tv.tv_sec = bIsTimeOut ? 5 : 60; // Wait for 1 minute in normal case, if time out happens
tv.tv_usec = 0; // Send heartbeat pkt and wait for 5 seconds for response
FD_ZERO(&rdfs);
FD_SET(sock,&rdfs);
nRet = select(sock+1, &rdfs, (fd_set *)0, (fd_set *)0, (struct timeval *)&tv);
//log mesg --returnValue[%d] receivedLength[%d], nRet, g_RcvLen
if (nRet < 0) {
//log mesgreturnValue = -1
return -1;
}
else if(nRet == 0)
{
if(!bIsTimeOut)
{
//Timeout happened, send heart beat
bIsTimeOut = true;
if (strlen(szServerIp) > 0) {
// send heart beat packet
hbInvokeId = SendRequest(szBuf, NULL);
}
else
hbInvokeId = SendRequest("<Echo>APIXport HB</Echo>", NULL);
}
else {
//Timeout happened, No response for heart beat
m_packet[atoi(hbInvokeId)].inUse = false;
return -1;
}
}
else if (nRet > 0)
{
bIsTimeOut = false; //***
if(FD_ISSET(sock,&rdfs))
{
if (g_RcvLen < 2)
{
//log mesg receivedLength[%d] < 2, g_RcvLen
// read header
nRet = recv(sock,&g_RcvBuf[g_RcvLen], 1, 0);
if (nRet <= 0)
{
// log mesg --Recvd Improper Header
return -1;
}
// receive two successive zeros..frame header
if (g_RcvBuf[g_RcvLen] == 0) g_RcvLen++;
else g_RcvLen = 0;
//log mesg receivedLength[%d] < 2 at --end returnValue[%d], g_RcvLen, nRet
}
else if (g_RcvLen < 4)
{
// log mesg --receivedLength[%d] < 4, g_RcvLen
// read length
nRet = recv(sock, &g_RcvBuf[g_RcvLen], 1, 0);
if (nRet <= 0) {
//Recvd Improper Length
return -1;
}
g_RcvLen++;
//log mesg --receivedLength[%d] < 4 --end returnValue[%d]", g_RcvLen, nRet
logMsg(strMsg, VERBOSE);
}
else if (g_RcvLen >= 4)
{
// try to receive full packet
tmplen= (unsigned short*)&g_RcvBuf[2];
pktlen = ntohs(*tmplen);
nRet = recv(sock, &g_RcvBuf[g_RcvLen], pktlen-g_RcvLen, 0);
if (nRet <= 0) {
//log -- Recvd Invalid Packet
return -1;
}
g_RcvLen += nRet; // add only received number of bytes
//log mesg --receivedLngth[%d] >= 4 --end returnValue[%d], g_RcvLen, nRet
if (g_RcvLen == pktlen)
{
// full packet received
return (g_RcvLen); // exit with length
}
}
}
}
}
return g_RcvLen;
}