The function below reads incoming data perfectly but only if the last data chunk is smaller than BUFFSIZE
. If the size of the last buff
happens to be equal to BUFFSIZE
, then the program tries to recv
again in the next loop iteration and sets bytes
to 1844674407379551615 (most probably integer overflow) and repeats this in an infinite loop... Why? Why isn't it 0? And why doesn't it escape the loop at this stage?
std::string getMsg (int clientFileDescriptor, int timeout_sec)
{
std::string msg;
msg.reserve(BUFFSIZE * 10);
char buff[BUFFSIZE + 1];
signal(SIGPIPE, SIG_IGN);
//set a timeout for reading and writing
struct timeval tv;
tv.tv_sec = timeout_sec;
tv.tv_usec = 0;
setsockopt (clientFileDescriptor, SOL_SOCKET, SO_RCVTIMEO, (const char*)&tv, sizeof(tv));
while (true)
{
size_t bytes = recv (clientFileDescriptor, buff, BUFFSIZE, 0);
std::cout << "bytes read: " << bytes << std::endl;
if (0 < bytes && bytes <= BUFFSIZE)
{
msg.append(buff, bytes);
//'buff' isn't full so this was the last chunk of data
if (bytes < BUFFSIZE)
break;
}
else if (!bytes) //EOF or socket shutdown by the client
{
break;
}
else
{
if (errno == EAGAIN || errno == EWOULDBLOCK || errno == EINTR)
continue;
//We cannot continue due to other erros (e.g. EBADF/socket not available)
break;
}
}
return msg;
}
Probably size_t
is unsigned on your platform. So if the recv
times out, recv
returns -1 and bytes
overflows. Your code doesn't correctly handle this case due to the overflow.
This is just wrong:
//'buff' isn't full so this was the last chunk of data
It's entirely possible buff
wasn't full because the last chunk of data hadn't been received yet. Tou should actually add code to detect the end of a message rather than relying on a timeout to find it for you if your application protocol supports messages of different sizes.
Unfortunately, you haven't given us the code for the other end of the connection nor specified how your application protocol works, so I have no idea what the other side does or expects. So it's not possible to give you more useful suggestions.