Архитектура Аудит Военная наука Иностранные языки Медицина Металлургия Метрология
Образование Политология Производство Психология Стандартизация Технологии


Приоритетное прерывание обслуживания



Приоритетное прерывание обслуживания - это переключение одной задачи на другую. Мы упоминали как schedule () и scheduler_tick() решают, на какую задачу переключиться далее, но мы еще не описали, как Linux решает, когда выполнить пере­ключение. В ядре 2.6 представлено приоритетное прерывание обслуживания, означающее, что как программы пользовательского пространства, так и программы про­странства ядра могут быть переключены в одно и то же время. Так как в Linux 2.6 при­оритетное прерывание обслуживания является стандартным, мы опишем, как работает приоритетное прерывание обслуживания для ядра и пользовательских задач в Linux.

Явное приоритетное прерывание обслуживания в ядре

Проще всего понять явное приоритетное прерывание обслуживания в ядре. Оно происхо­дит в пространстве ядра, когда код ядра вызывает schedule (). Код ядра может вызы­вать schedule () двумя способами: либо с помощью прямого вызова schedule О, либо с помощью блокировки.

Когда происходит явное приоритетное прерывание обслуживания в ядре, как, напри­мер, в драйвере устройства, ожидающем в wait_queue, управление просто передается планировщику и для выполнения выбирается новая задача.

7.2.2 Неявное пользовательское приоритетное
прерывание обслуживания

Когда ядро завершает обработку задачи пользовательского пространства и готово пере­дать управление задаче пользовательского пространства, оно сперва проверяет, какой за­даче можно передать управление. Это не должна быть задача пользовательского про­странства, которая передает управление ядру. Например, если задача А порождает сис­темный вызов, после завершения системного вызова ядро передает управление системой задаче В.

Каждая задача в системе имеет флаг «необходимости перепланировки», который ус­танавливается, когда задачу следует перепланировать:



Глава 7 • Планировщик и синхронизация ядра


include/linux/sched.h

988 static inline void set_tsk_need_resched(struct task_struct *tsk)

989 {

990 set_tsk_thread_flag(tsk, TIFJSTEED_RESCHED);

991 }
992

993 static inline void clear_tsk_need_resched(struct task_struct *tsk)

994 {

995 clear_tsk_thread_flag(tsk, TIF_NEED_RESCHED); }

1003 static inline int need__resched(void)

1004 {

1005 return unlikely (test_thread_f lag (TIF_NEED_RESCHED) );

1006 }

Строки 988-996

Интерфейсы set__tsk_need_resched и clear_tsk_need_resched позво­ляют устанавливать архитектурно-специфический флаг TIF_NEED_RESCHED.

Строки 1003-1006

need_resched проверяет, установлен ли TIF_NEED_RESCHED во флаге текуще­го процесса.

Когда ядро возвращается в пользовательское пространство, оно выбирает процесс, которому нужно передать управление, как описано в schedule () и scheduler_ tick(). Тогда как scheduler_tick() может пометить задачу как требующую перепланировки, только schedule () может манипулировать этим знанием; sched­ule () циклически выбирает новую задачу для выполнения до тех пор, пока новая выбранная задача не потребует перепланировки. После завершения schedule () новая задача получает управление процессором.

Поэтому, пока процесс запущен, системный таймер порождает прерывания, запус­кающие scheduler_tick(); scheduler_tick() может помечать задачу как тре­бующую перепланировки и перемешает ее в массив истекших. При завершении операций ядра за scheduler_tick() могут следовать другие прерывания и ядро будет переда­вать управление процессором, a schedule () вызываться для выбора следующей запус­каемой задачи. Поэтому scheduler_tick() отмечает процессы и сортирует очереди, но schedule () выбирает следующую задачу и передает управление процессором.

Неявное приоритетное прерывание обслуживания ядра

В Linux 2.6 реализовано новое неявное приоритетное прерывание обслуживания ядра. Когда задача ядра получает управление процессором, его обслуживание может приори-


Приоритетное прерывание обслуживания



тетно прерываться только другой задачей ядра, если она не содержит никаких блокиро­вок. Каждая задача имеет поле preempt_count, помечающее задачу как приоритетно прерываемую. Счетчик увеличивается каждый раз, когда задача блокируется, и уменьша­ется, когда разблокируется. Функция schedule () отключает приоритетное прерывание обслуживания, когда определяет, какую задачу запустить следующей.

Существует две возможности для неявного приоритетного прерывания обслужива­ния ядра: либо код ядра вызывается из блока кода, для которого отключено приоритетное прерывание обслуживания, или процесс возвращается в код ядра из прерывания. Если управление возвращается в пространство ядра из прерывания, прерывание вызывает schedule () и новая задача вызывается тем же, описанным выше способом.

Если код ядра вызывается из блока кода с отключенным приоритетным прерыванием обслуживания, включение приоритетного прерывания обслуживания может привести к приоритетному прерыванию обслуживания текущей задачи:

include/linux/preempt.h

46 #define preempt__enable() \

47 do { \

 

48 preempt_enable_no_resched(); \

49 preempt_check__resched(); \

50 } while (0)

Строки 46-50

preempt__enable () вызывает preempt_enable_no_resched(), умень­шающую preempt_count текущей задачи на единицу, и затем вызывает preempt_check_resched ().

include/linux/preempt.h

40 #define preempt_check_resched() \

41 do { \

42 if (unlikely(test_thread_flag(TIF_NEED_RESCHED) ) ) \

43 preempt_schedule(); \

44 } while (0)

Строки 40-44

Preempt_check_resched () смотрит, помечена ли текущая задача как требующая перепланировки; если это так, вызывается preempt_schedule ().

kernel/sched.с

2328 asmlinkage void _ sched preempt_schedule(void)

2329 {



Глава 7 • Планировщик и синхронизация ядра


2330 struct thread_info *ti = current_thread__inf о ();
2331

2332 /*

2333 * Если отключено ненулевое количество preempt__count или

233 4 * прерываний, мы не хотим приоритетно прерывать обслуживание

233 5 * текущей задачи. Просто возвращаемся. */

2336 if (unlikely(ti-> preempt__count || irqs_disabled() ) )

233 7 return;

233 9 need_resched:

2340 ti-> preempt__count = PREEMPT_ACTI VE;

2341 scheduleO;

2342 ti-> preempt_count = 0; 2343

2344 /* мы можем потерять возможность приоритетного прерывания

обслуживания между планировщиком и текущим моментом */

2345 barrier();

2346 if (unlikely (test_thread_flag(TIF_NEED_RESCHED) ) )

2347 goto need__resched;

2348 }

Строки 2336-2337

Если текущая задача все еще имеет положительное значение preempt_count, как при рекурсивной команде preempt_disable (), или если для текущей задачи от­ключены прерывания, мы возвращаем управление процессором текущей задаче.

Строки 2340-2347

Текущая задача не имеет блокировок, так как preempt_count равно 0, a IRQ вклю­чены. Поэтому мы устанавливаем preempt_count текущей задачи для обозначе­ния входящего приоритетного прерывания обслуживания и вызываем schedule (), выбирающую другую задачу.

Если задача запущена из кода, требующего перепланировки, ядру нужно удосто­вериться, что у текущей задачи можно забрать управление процессором. Ядро проверяет значение preempt_count задачи. Если preempt_count равно 0 и поэтому текущая задача не содержит блокировок, вызывается schedule () и для выполнения выбирается новая задача. Если preempt_count не равно 0, передавать управление другой задаче не­безопасно, а управление возвращается в текущую задачу до тех пор, пока с нее не будут сняты все блокировки. Когда текущая задача освобождает блокировку, проверяют, требу­ет ли задача перепланировки. Когда текущая задача освобождает последнюю блокировку и preempt_count достигает 0, производится немедленное перепланирование.


Поделиться:



Популярное:

  1. V. ТИПОВАЯ ФРАЗЕОЛОГИЯ РАДИООБМЕНА ДИСПЕТЧЕРОВ ОРГАНОВ ОБСЛУЖИВАНИЯ ВОЗДУШНОГО ДВИЖЕНИЯ (УПРАВЛЕНИЯ ПОЛЕТАМИ) С ЭКИПАЖАМИ ВОЗДУШНЫХ СУДОВ
  2. Виды технического обслуживания.
  3. Влияние технического обслуживания и ремонта на эффективность использования судов
  4. Глава 24. Минимальные расчетные показатели обеспечения объектами социального обслуживания системы социальной защиты населения.
  5. Глава 42. Минимальные расчетные показатели обеспечения объектами для хранения и обслуживания транспортных средств
  6. Гражданско-правовые способы защиты прав владельцев товарных знаков, знаков обслуживания, наименований места происхождения товаров
  7. Гримерный. Структура гримерного цеха- грим, пастиж, пластика. Виды обслуживания съемочных групп.
  8. Если согласие женщины будет отсутствовать, то такое прерывание беременности, следует рассматривать как причинение вреда здоровью.
  9. Местного комитета обслуживания АН Санкт-Петербурга
  10. Методика расчета норм обслуживания
  11. Методика расчета оптимальных норм обслуживания
  12. Моделирование систем массового обслуживания. Переход детерминированных систем к хаотическому поведению.


Последнее изменение этой страницы: 2016-03-25; Просмотров: 784; Нарушение авторского права страницы


lektsia.com 2007 - 2024 год. Все материалы представленные на сайте исключительно с целью ознакомления читателями и не преследуют коммерческих целей или нарушение авторских прав! (0.015 с.)
Главная | Случайная страница | Обратная связь