Настоящий обработчик прерывания

Настоящий обработчик прерывания

Давайте рассмотрим настоящий обработчик прерывания, который используется в драйвере устройства RTC (real-time clock, часы реального времени), находящегося в файле drivers/char/rtc.c. Устройство RTC есть во многих вычислительных системах, включая персональные компьютеры (PC). Это отдельное от системного таймера устройство, которое используется для установки системных часов, для подачи сигналов таймера (alarm) или для реализации генераторов периодических сигналов (periodic timer). Установка системных часов обычно производится путем записи значений в специальный регистр или диапазон адресов (номеров портов) ввода-вывода (I/O range). Подача сигналов таймера или генератор периодических сигналов обычно реализуются через прерывания. Прерывание эквивалентно некоторому сигналу таймера: оно генерируется, когда истекает период времени сигнального таймера. При загрузке драйвера устройства RTC вызывается функция rtc_init() для инициализации драйвера. Одна из ее обязанностей — это регистрация обработчика прерывания. Делается это следующим образом.

if (request_irq(RTC_IRQ, rtc_interrupt, SA_INTERRUPT, "rtc", NULL) {

 printk(KERN_ERR "rtc: cannot register IRQ %d " , rtc_irq);

 return -EIO;

}

Из данного примера видно, что номер линии прерывания — это константа RTC_IRQ, значение которой определяется отдельно для каждой аппаратной платформы с помощью препроцессора. Например, для персональных компьютеров это значение всегда соответствует IRQ 8. Второй параметр— это обработчик прерывания, rtc_interrupt, при выполнении которого запрещены все прерывания в связи с указанием флага SA_INTERRUPT. Из четвертого параметра можно заключить, что драйвер будет иметь имя "rtc". Так как наше устройство не может использовать линию прерывания совместно с другими устройствами и обработчик прерывания не используется для каких-либо других целей, в качестве параметра dev_id передается значение NULL.

И наконец, собственно сам обработчик прерывания.

/*

* Очень маленький обработчик прерывания. Он выполняется с

* установленным флагом SA_INTERRUPT, однако существует

* возможность конфликта с выполнением функции set_rtc_mmss()

* (обработчик прерывания rtc и обработчик прерывания системного

* таймера могут выполняться одновременно на двух разных

* процессорах). Следовательно, необходимо сериализировать доступ

* к микросхеме с помощью спин-блокировки rtc_lock, что должно

* быть сделано для всех аппаратных платформ в коде работы с

* таймером. (Тело функции set_rtc_mmss() ищите в файлах

* ./arch/XXXX/kernel/time.c)

*/

static irqreturn_t rtc_interrupt(int irq, void *dev_id,

 struct pt_regs *regs) {

 /*

 * Прерывание может оказаться прерыванием таймера, прерыванием

 * завершения обновления или периодическим прерыванием.

 * Состояние (причина) прерывания хранится в самом

 * младшем байте, а общее количество прерывание — в оставшейся

 * части переменной rtc_irq_data

 */

 spin_lock(&rtc_lock);

 rtc_irq_data += 0x100;

 rtc_irq_data &= ~0xff;

 rtc_irq_data |= (CMOS_READ(RTC_INTR_FLAGS) & 0xF0);

 if (rtc_status & RTC_TIMER_ON)

  mod_timer(&rtc_irq_timer, jiffies + HZ/rtc_freq + 2*HZ/100);

 spin_unlock(&rtc_lock);

 /*

 * Теперь выполним остальные действия

 */

 spin_lock(&rtc_task_lock);

 if (rtc_callback)

  rtc_callback->func(rtc_callback->private_data);

 spin_unlock(&rtc_task_lock);

 wake_up_interruptible(&rtc_wait);

 kill_fasync(&rtc_async_queue, SIGIO, POLL_IN);

 return IRQ_HANDLED;

}

Эта функция вызывается всякий раз, когда система получает прерывание от устройства RTC. Прежде всего, следует обратить внимание на вызовы функций работы со спин-блокировками: первая группа вызовов гарантирует, что к переменной rtc_irq_data не будет конкурентных обращений другими процессами на SMP-машине, а вторая — защищает в аналогичной ситуации параметры структуры rtc_callback. Блокировки обсуждаются в главе 9, "Средства синхронизации в ядре".

Переменная rtc_irq_data содержит информацию об устройстве RTC и обновляется с помощью функции mod_timer(). О таймерах рассказывается в главе 10, "Таймеры и управление временем".

Последняя часть кода, окруженная спин-блокировками, выполняет функцию обратного вызова (callback), которая может быть установлена извне. Драйвер RTC позволяет устанавливать функцию обратного вызова, которая может быть зарегистрирована пользователем и будет исполняться при каждом прерывании, приходящем от устройства RTC.

В конце функция обработки прерывания возвращает значение IRQ_HANDLED, чтобы указать, что прерывание от данного устройства обработано правильно. Так как этот обработчик прерывания не поддерживает совместное использование линий прерывания и не существует механизма, посредством которого обработчик прерываний RTC может обнаружить вложенные запросы на прерывание, то этот обработчик всегда возвращает значение IRQ_HANDLED.

Поделитесь на страничке

Следующая глава >

Похожие главы из других книг

ОКНО ДИАЛОГА: Настоящий индеец

Из книги Журнал «Компьютерра» № 22 от 12 июня 2007 года автора Журнал «Компьютерра»

ОКНО ДИАЛОГА: Настоящий индеец Автор: Илья Щуров Voyager«Я был в России в прошлый раз двадцать лет назад в составе туристической группы – в городе, который назывался Ленинградом (в Санкт-Петербурге я не был никогда), – рассказывает Брайен Белендорф (Brian Behlendorf), пока мы ищем


Универсальный обработчик исключений

Из книги Microsoft Visual C++ и MFC. Программирование для Windows 95 и Windows NT автора Фролов Александр Вячеславович

Универсальный обработчик исключений В одном блоке try можно вызывать исключения разных типов. В этом случае после блока try должны следовать обработчики для исключений каждого типа. Вы можете определить обработчик, обслуживающий исключения всех типов. Для этого вместо


Пример: обработчик управляющих сигналов консоли

Из книги Системное программирование в среде Windows автора Харт Джонсон М

Пример: обработчик управляющих сигналов консоли В программе 4.5 организован бесконечный цикл, в котором каждые 5 секунд вызывается функция Веер, подающая звуковой сигнал. Пользователь может завершить выполнение программы, нажав комбинацию клавиш <Ctrl+C> или закрыв


Обработчик управляющих команд службы

Из книги Настоящий профессионал и настоящий ламер автора Артамонов Вадим

Обработчик управляющих команд службы Обработчик управляющих команд службы, то есть функция косвенного вызова, определяемая с помощью функции RegisterServiceCtrlHandlerEx, имеет следующий прототип:  DWORD WINAPI HandlerEx(DWORD dwControl, DWORD dwEventType, LPVOID lpEventData, LPVOID lpContext)  dwControl — обозначает


Вадим Артамонов Настоящий профессионал и настоящий ламер

Из книги Тайм-менеджмент для системных администраторов автора Лимончелли Томас

Вадим Артамонов Настоящий профессионал и настоящий ламер 15 признаков настоящего профессионала 1. Располагает все части компьютера так, чтобы было удобно работать, хотя со стороны это выглядит неэстетично.2. Имеет на рабочем месте кофеварку и пепельницу. Чтобы меньше


Прерывания

Из книги Цифровой журнал «Компьютерра» № 166 автора Журнал «Компьютерра»

Прерывания Прерывания неизбежны. Это естественная часть нашей работы, и от нас зависит, насколько хорошо мы с ними справляемся.Работать под управлением прерываний означает выполнять задания по мере их поступления, а не в соответствии с какой-то системой приоритетов,


По стопам Аарона Шварца: за что посадили Эндрю Арнхаймера и почему настоящий хакер должен молчать? Евгений Золотов

Из книги Введение в QNX/Neutrino 2. Руководство по программированию приложений реального времени в QNX Realtime Platform автора Кёртен Роб

По стопам Аарона Шварца: за что посадили Эндрю Арнхаймера и почему настоящий хакер должен молчать? Евгений Золотов Опубликовано 29 марта 2013 Когда в январе Сеть прощалась с Аароном Шварцем, казалось, в истории информационных технологий начинается новая эра.


Прерывания

Из книги Разработка ядра Linux автора Лав Роберт

Прерывания В этой главе вы научитесь писать обработчики прерываний для QNX/Neutrino и узнаете, как обработчики прерываний влияют на диспетчеризацию


QNX/Neutrino и прерывания

Из книги автора

QNX/Neutrino и прерывания В данной главе мы рассмотрим прерывания, как с ними работать в QNX/Neutrino, их воздействие на диспетчеризацию и режим реального времени, а также некоторые стратегии их использования.Первый вопрос, который приходит на ум: «А что такое прерывание?»Прерывание


Обработчик прерывания

Из книги автора

Обработчик прерывания Давайте рассмотрим собственно обработчик прерывания. В первом примере применим InterruptAttach(), а затем рассмотрим аналогичный случай, только с применением функции InterruptAttachEvent().Применение функции InterruptAttach()В продолжение примера приведем функцию intHandler()


Прерывания

Из книги автора

Прерывания Прерывания позволяют аппаратным устройствам взаимодействовать с процессором. Например, при наборе на клавиатуре контроллер клавиатуры (или другое устройство, которое обслуживает клавиатуру) генерирует прерывание, чтобы объявить операционной системе о том,


Контекст прерывания

Из книги автора

Контекст прерывания При выполнении обработчика прерывания или обработчика нижней половины, ядро находится в контексте прерывания. Вспомним, что контекст процесса — это режим, в котором работает ядро, выполняя работу от имени процесса, например выполнение системного


Обработчик прерываний таймера

Из книги автора

Обработчик прерываний таймера Теперь, когда мы разобрались, что такое jiffies и HZ, а также какова роль системного таймера, рассмотрим реализацию обработчика прерываний системного таймера. Обработчик прерываний таймера разбит на две части: часть, зависимую от аппаратной