2013-02-28 3 views
2

Целью является считывание данных из сокета без блокировки. Страница Linux Руководство говорит:Когда recv блокирует?

принимать вызовы обычно возвращают какие-либо данные, вплоть до запрашиваемой суммы, а не ждать получения полной суммы запрошенной.

Означает ли это, что я не должен пройти MSG_DONTWAIT флаг recv() после опроса дескриптор сокета с select()/poll()/epoll()?

ответ

4

Поведение recv/read зависит от характеристик самого разъема. Если сокет отмечен как неблокирующий, эти вызовы должны немедленно возвращать EAGAIN/EWOULDBLOCK, а не блокировать процесс.

Розетка может быть помечена как неблокирующая перед ее чтением, обычно через fcntl или ioctl.

В этом отрывке из руководства говорится, что, как правило, считывание как блокирующих, так и неблокирующих сокетов не требуется для заполнения всего поставляемого буфера. Вот почему важно проверить результат вызовов recv/read, чтобы узнать, сколько буфера содержит фактические данные и сколько мусора.

Это не очень хорошая идея вообще использовать блокирующие сокеты в сочетании с опросом IO вызовы, такие как select/poll/epoll. Даже если вызов опроса указывает, что конкретный сокет готов к чтению, блокирующий сокет иногда все еще блокируется.

+1

Я бы также сказал, что то, что считается «блокировкой», также зависит от драйвера, который фактически реализует вызовы 'read',' write' и 'poll' для данного сокета/inode. Иногда у них есть своя таинственная точка зрения на то, что блокируется, а что нет ... – 2013-02-28 13:34:13

+0

@Blagobest. В настоящее время я сталкиваюсь с проблемой, что epoll (режим триггера уровня) сообщает мне, что сокет fd доступен для чтения, когда я заблокирован, а вызывая recv(). Ваш ответ кажется разумным противником, что я видел. Могу ли я спросить, какие возможные причины приводят к побочным пробуждениям на epoll(), СПАСИБО? – kai

+0

@kai: У меня такая же ситуация и тот же вопрос. http://stackoverflow.com/q/41679836/560648 –

Смежные вопросы