Изменено ли время ожидания после вызова для выбора в c? - PullRequest
0 голосов
/ 10 декабря 2010

В своем назначении на программирование сокетов я сделал вызов select следующим образом:

select(s+1, &rfds, (fd_set *)0, (fd_set *)0,&tv)

, где tv типа struct timeval

Я прочитал страницу руководства по select и сказал::

В Linux функция выбора изменяет время ожидания, чтобы отразить количество времени бездействия;большинство других реализаций не делают этого.Это вызывает проблемы как в случае, когда код Linux, который считывает тайм-аут, переносится в другие операционные системы, так и в случае, когда код переносится в Linux, который повторно использует struct timeval для множественного выбора в цикле без его повторной инициализации.Считайте, что тайм-аут не определен после возврата select.

Означает ли это, что моя переменная tv будет изменена после вызова select?(Я использую Ubuntu)

Ответы [ 5 ]

6 голосов
/ 10 декабря 2010

Да, это так.Для переносимости вы должны повторно инициализировать его перед каждым вызовом select.

5 голосов
/ 10 декабря 2010

Переменная будет по-прежнему указывать на ту же структуру, но содержимое структуры будет изменено.

3 голосов
/ 10 декабря 2010

Также обратите внимание, что при ошибке содержимое структуры timeval не определяется при возврате select ().Поскольку вы не можете гарантировать, что не получите ошибку (EINTR является наиболее распространенным), вам понадобится механизм для отслеживания оставшегося времени (если вам это нужно), так что использование содержимого структуры timeval после возврата является пустой тратой времени вбольшинство ситуаций даже без проблем с переносимостью.

2 голосов
/ 10 декабря 2010

Из POSIX:

После успешного завершения функция select () может изменить объект, на который указывает аргумент timeout.

Нет никаких требований, поэтому переносимый код не должен полагаться на значения в структуре timeout после возврата select и должен сбрасывать их, если они снова нужны. См:

http://www.opengroup.org/onlinepubs/9699919799/functions/select.html

1 голос
/ 10 декабря 2010

Очень важное примечание: select () будет не всегда уменьшать значение тайм-аута.

В общем случае, если select () не возвращается немедленно, оно будет уменьшать значение

Когда вызывается select (), , если данные уже ожидают , несмотря на то, что вызову select требуется немного времени для выполнения, тайм-аут не уменьшается .

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

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...