Прерывание epoll_wait с событием без ввода-вывода, без сигналов - PullRequest
9 голосов
/ 11 февраля 2010

Текущий сценарий - epoll_wait для нескольких fds и очереди возможных входящих сообщений. Я бы хотел, чтобы цикл ниже epoll_wait выполнялся для события ввода-вывода или для нового сообщения.
Способы, которые я знаю:

  • Используйте тайм-аут time мс и сначала проверьте очередь в цикле
  • Используйте трюк для самостоятельной передачи из кода очереди, когда сообщения станут доступны
  • Прервать системный вызов стандартным сигналом
  • Используйте epoll_pwait и уточните предыдущий пункт

Ни один из пунктов, приведенных выше, не удовлетворяет меня достаточно, и мне было интересно, есть ли другие методы, которые я не нашел.
Причины:

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

идеи?

Ответы [ 2 ]

19 голосов
/ 15 февраля 2010

Вы можете использовать eventfd , который фактически совпадает с трюком с самоотводом, за исключением меньшего количества файловых дескрипторов и меньшего количества шаблонов (например, glibc имеет удобные функции eventfd_read/write).

1 голос
/ 15 февраля 2010

Вы перечислили события, которые могут разбудить Эполла, поэтому на самом деле возникает вопрос: «Как мне уменьшить шаблон для трюка с самотрубкой?»

Ответ на этот вопрос действительно зависит от вашего кода, языка и того, что вы пытаетесь сделать. Я предполагаю, что у вас есть поток, который обрабатывает ввод / вывод, и вы хотите выполнять другую работу в этом потоке, пока ввод / вывод не готов. В коде, который управляет циклом epoll, он может иметь внутренний дескриптор, который предоставляется другим частям системы в качестве функции «пробуждения» или «отправки работы».

Есть библиотеки, которые делают это, например boost.asio для C ++. Тем не менее, написать свой собственный нетрудно, если вы просто нацеливаетесь на epoll, и количество действительного стандартного кода должно быть минимальным, если у вас есть класс / модуль / что-нибудь, что имеет дело с циклом epoll.

...