Сообщение epoll от 06.12.2022 14:34
Изменено 06.12.2022 14:35 maks1180
epoll
Задача стандартная — сетевое приложение, которое отвечает на входящие запросы.
Нужно получать уведомление если:
1) EPOLLIN (на чтение) — есть что прочитать из сокета (т.е. следим за состоянием).
2) EPOLLOUT (для записи) нужно получать уведомление только при смене состояния (т.е. следим за изменением состояния) на возможность записи, т.е. если раньше нельзя было писать а теперь можно.
Как я понял данная задача не решается через epoll, так как если я вызову epoll_ctl
1) с флагом EPOLLET то не буду получать нотификацию EPOLLIN до следующих принятых данных, если прочитаю не всё что есть в сокете
2) без флага EPOLLET, то буду постоянно получать EPOLLOUT
Вариант №1 вызываем epoll_ctl( EPOLLET + EPOLLIN+EPOLLOUT)
не буду получать нотификацию EPOLLIN до следующих принятых данных, если прочитаю не всё что есть в сокете.
Как понять, что я всё прочитал из сокета ?
Вариант №2 вызываем epoll_ctl( EPOLLIN+EPOLLOUT) — без EPOLLET
буду постоянно получать EPOLLOUT, придёться постоянно вызывать epoll_ctl, что-бы снять или поставить EPOLLOUT. Это же функция ядра и вызов будет занимать время значительное ?
Вроде libuv так делает.
Какие ёще есть решения ?
Может быть сделать 2 epoll, один для чтения, другой для записи ? Тогда их из разных потоков нужно вызывать ?
Нужно получать уведомление если:
1) EPOLLIN (на чтение) — есть что прочитать из сокета (т.е. следим за состоянием).
2) EPOLLOUT (для записи) нужно получать уведомление только при смене состояния (т.е. следим за изменением состояния) на возможность записи, т.е. если раньше нельзя было писать а теперь можно.
Как я понял данная задача не решается через epoll, так как если я вызову epoll_ctl
1) с флагом EPOLLET то не буду получать нотификацию EPOLLIN до следующих принятых данных, если прочитаю не всё что есть в сокете
2) без флага EPOLLET, то буду постоянно получать EPOLLOUT
Вариант №1 вызываем epoll_ctl( EPOLLET + EPOLLIN+EPOLLOUT)
не буду получать нотификацию EPOLLIN до следующих принятых данных, если прочитаю не всё что есть в сокете.
Как понять, что я всё прочитал из сокета ?
Вариант №2 вызываем epoll_ctl( EPOLLIN+EPOLLOUT) — без EPOLLET
буду постоянно получать EPOLLOUT, придёться постоянно вызывать epoll_ctl, что-бы снять или поставить EPOLLOUT. Это же функция ядра и вызов будет занимать время значительное ?
Вроде libuv так делает.
Какие ёще есть решения ?
Может быть сделать 2 epoll, один для чтения, другой для записи ? Тогда их из разных потоков нужно вызывать ?
epoll
Задача стандартная — сетевое приложение, которое отвечает на входящие запросы.
Нужно получать уведомления:
1) EPOLLIN (на чтение) — если есть что прочитать из сокета (т.е. следим за состоянием).
2) EPOLLOUT (на запись) — только при смене состояния (т.е. следим за изменением состояния) на возможность записи, т.е. если раньше нельзя было писать а теперь можно.
Как я понял данная задача не решается через epoll, так как если я вызову epoll_ctl
1) с флагом EPOLLET то не буду получать нотификацию EPOLLIN до следующих принятых данных, если прочитаю не всё что есть в сокете
2) без флага EPOLLET, то буду постоянно получать EPOLLOUT
Вариант №1 вызываем epoll_ctl( EPOLLET + EPOLLIN+EPOLLOUT)
не буду получать нотификацию EPOLLIN до следующих принятых данных, если прочитаю не всё что есть в сокете.
Как понять, что я всё прочитал из сокета ?
Вариант №2 вызываем epoll_ctl( EPOLLIN+EPOLLOUT) — без EPOLLET
буду постоянно получать EPOLLOUT, придёться постоянно вызывать epoll_ctl, что-бы снять или поставить EPOLLOUT. Это же функция ядра и вызов будет занимать время значительное ?
Вроде libuv так делает.
Какие ёще есть решения ?
Может быть сделать 2 epoll, один для чтения, другой для записи ? Тогда их из разных потоков нужно вызывать ?
Нужно получать уведомления:
1) EPOLLIN (на чтение) — если есть что прочитать из сокета (т.е. следим за состоянием).
2) EPOLLOUT (на запись) — только при смене состояния (т.е. следим за изменением состояния) на возможность записи, т.е. если раньше нельзя было писать а теперь можно.
Как я понял данная задача не решается через epoll, так как если я вызову epoll_ctl
1) с флагом EPOLLET то не буду получать нотификацию EPOLLIN до следующих принятых данных, если прочитаю не всё что есть в сокете
2) без флага EPOLLET, то буду постоянно получать EPOLLOUT
Вариант №1 вызываем epoll_ctl( EPOLLET + EPOLLIN+EPOLLOUT)
не буду получать нотификацию EPOLLIN до следующих принятых данных, если прочитаю не всё что есть в сокете.
Как понять, что я всё прочитал из сокета ?
Вариант №2 вызываем epoll_ctl( EPOLLIN+EPOLLOUT) — без EPOLLET
буду постоянно получать EPOLLOUT, придёться постоянно вызывать epoll_ctl, что-бы снять или поставить EPOLLOUT. Это же функция ядра и вызов будет занимать время значительное ?
Вроде libuv так делает.
Какие ёще есть решения ?
Может быть сделать 2 epoll, один для чтения, другой для записи ? Тогда их из разных потоков нужно вызывать ?