У меня есть драйвер устройства, где оборудование постоянно передает данные в кольцевой буфер в пространстве ядра.Когда пользователь вызывает read()
, данные перемещаются из этого буфера в буфер вызывающего.Прерывание срабатывает, если оборудование заполняет дескриптор DMA (т. Е. Готово больше данных) или если оборудование обнаружило ошибку.В любом случае обработчик прерываний планирует выполнение работы в нижней половине.
В нижней половине выясняется, было ли прерывание вызвано аппаратным сбоем или доступностью данных.В любом случае он устанавливает некоторые флаги, чтобы системный вызов read()
знал, что произошло.После установки указанных флагов нижняя половина вызывает wake_up_interruptible(&my_waitqueue);
В системном вызове read()
я хочу заблокировать на некоторое время, если в буфере ядра нет данных.Если время ожидания истекло, я просто сообщаю звонящему, что данные недоступны.В результате я вызываю wait_event_interruptible_hrtimeout(my_waitqueue, (error || data_ready), my_timeout);
По сути, я блокирую ожидание либо условия ошибки, либо доступности данных.
Мой вопрос касается того, упорядочены ли эти потоки (т. Е. Нижняя половина иread()
вызов) имеет значение.В частности, мне интересно, всегда ли wait_event_interruptible_hrtimeout()
ждет, когда кто-нибудь разбудит его?Что, если был предыдущий вызов wake_up_interruptible()
?
Сказано иначе, я обеспокоен следующим сценарием:
- Прерывания из-за аппаратного сбоя.Помните, что передачи в циклический буфер происходят независимо от системного вызова
read()
. - Нижняя половина выполнения, помечает передачу как неудачную и вызывает
wake_up_interruptible()
.Обратите внимание, что поскольку это аппаратный сбой, прерывания больше не будут срабатывать, и мы не будем запускать нижнюю половину снова, пока устройство не будет перезагружено. - Пользовательский процесс хочет получить больше данных и вызывает
read()
.Теперь мы попали в строку кода, содержащую wait_event_interruptible_hrtimeout()
.Блокируем ли мы ожидание, чтобы проснуться, или очередь ожидания знает о предыдущем вызове на wake_up_interruptible()
?
В основном мне интересно, нужно ли мне сначала проверить условие, которое я передал в wait_event_interruptible_hrtimeout()
(т.е. (error || data_ready)
) перед вызовом wait_event_interruptible_hrtimeout()
.