Подтвердить что ты не робот

Когда нужно проверить EINTR и повторить вызов функции?

Я программирую пользовательское приложение для встроенной системы Linux, и я использую общие функции, такие как open, close, read, ioctl и т.д. для устройств. Теперь, я прочитал об EINTR, указывает, что функция была прервана сигналом, но я не уверен в последствиях. Во всех примерах программ, которые у меня есть, иногда это делается, например. ioctl(), иногда это не делается, например. читать(). Итак, я немного смущен.

Когда я предпочитаю проверять EINTR и повторять вызов функции?

4b9b3361

Ответ 1

См. sigaction: http://pubs.opengroup.org/onlinepubs/009695399/functions/sigaction.html

SA_RESTART
  This flag affects the behavior of interruptible functions; that is, those 
  specified to fail with errno set to EINTR. If set, and a function specified 
  as interruptible is interrupted by this signal, the function shall restart 
  and shall not fail with EINTR unless otherwise specified. If the flag is not 
  set, interruptible functions interrupted by this signal shall fail with errno 
  set to EINTR.

По умолчанию у вас есть поведение SA_RESTART, поэтому вам не нужно беспокоиться об EINTR, если вы не играете с сигналами.

Ответ 2

Является ли ваше приложение управляемым событием? (Значение его основного цикла включает вызов select()/epoll_wait()).

В приложении, управляемом событиями, вы можете заблокировать все сигналы и только разблокировать их во время вызова pselect()/epoll_pwait(). Таким образом, остальная часть вашего кода никогда не будет иметь дело с EINTR.

Ответ 4

У меня была аналогичная проблема, ожидая ввода от именованного канала с помощью read().

Я нашел объяснение и полезный макрос для примитивов в Документация GNU libc: TEMP_FAILURE_RETRY

Пример:

TEMP_FAILURE_RETRY (read_return = read((int)example_fifo, buffer, (size_t)n));
if (read_return==-1){
    fprintf(stderr, "reader.c: read_fifo: read(): %s \n", strerror(errno));
    fflush(stderr);
}