C++ non-blocking reading

点点圈 提交于 2019-12-12 06:45:21

问题


All I need to do is just to read all available bytes from socket. But there is one condition: there is a method which reads n bytes from non-blocking socket which I have to use for implementation of another method which is going to read all available bytes.

Non-blocking reading of some data with defined size:

ssize_t read(void* buf, size_t len)
{
    ssize_t bytesRead = 0;
    ssize_t bytesTotallyRead = 0;
    size_t bytesLeftToRead = len;
    while (bytesTotallyRead < len)
    {
        bytesRead = ::recv(handle, (char*)buf+bytesTotallyRead, bytesLeftToRead, 0);
        if (bytesRead > 0)
        {
            bytesTotallyRead += bytesRead;
            bytesLeftToRead -= bytesRead;
        }
        else if (bytesRead == 0)
        {
            break;
        }
        else if (bytesRead < 0)
        {
            if (errno == EINTR)
            {
                continue;
            }
            else if (errno == EWOULDBLOCK)
            {
                int selectStatus(waitForIncomingData(500));
                if (selectStatus > 0)
                {
                    continue;
                }
                else
                {
                    break;
                }
            }
            else
            {
                break;
            }
        }
    }
    return (bytesRead==-1)?-1:bytesTotallyRead;
}

So I have to use this method to implement something like ssize_t readAllAvailable(std::vector<uint8_t> &data) which uses method above for it's implementation.

The problem here, as you see, that read() uses select() for waiting for incoming data so using of buffer of fixed size (in loop) might lead to 500 ms (in this concrete case) waiting after 1st iteration and this is definitely not the way it should be done.

Is it possible at all? I mean some efficient ways.


回答1:


there is a method which reads n bytes from socket asynchronously

No there isn't. There is a method which uses non-blocking mode and select() to reimplement blocking mode. There is nothing 'asynchronous' about it whatsoever. From the point of view of the caller it is blocking-mode. It is poorly, indeed incorrectly, conceived, and should be thrown away. The code you have posted is completely and utterly pointless. It's just a complicated way of implementing a blocking read loop. Use blocking mode. In effect, you already are, but with more system calls. And lose the select() call and EAGAIN/EWOUDLBLOCK stuff.

which I have to use for implementation of another method which is going to read all available bytes. ... The problem here, as you see, that read() uses select() for waiting for incoming data so using of buffer of fixed size (in loop) might lead to 500 ms (in this concrete case) waiting after 1st iteration

No it isn't. select() will return immediately data becomes available on the socket. No 500ms unless there is no data. And 'using a buffer of fixed size' has exactly nothing to do with it.

and this is definitely not the way it should be done.

It isn't the way it is done.

There is no problem here to solve.



来源:https://stackoverflow.com/questions/43078613/c-non-blocking-reading

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!