Разработка ядра Linux | страница 68



, определенной в файле >kernel/sched.c. Данная функция вызывается функцией >schedule(), когда новый процесс выбирается для выполнения. При этом выполняются следующие шаги.

• Вызывается функция >switch_mm(), которая определена в файле >include/asm/mmu_context.h и предназначена для переключения от виртуальной памяти старого процесса к виртуальной памяти нового процесса.

• Вызывается функция >switch_to(), определенная в файле >include/asm/system.h, для переключения от состояния процессора предыдущего процесса к состоянию процессора нового процесса. Эта процедура включает восстановление информации стека ядра и регистров процессора.

Ядро должно иметь информацию о том, когда вызывать функцию >schedule(). Если эта функция будет вызываться только тогда, когда программный код вызывает ее явно, то пользовательские программы могут выполняться неопределенное время. Поэтому ядро поддерживает флаг >need_resched для того, чтобы сигнализировать, необходимо ли вызывать функцию >schedule() (табл. 4.2). Этот флаг устанавливается функцией >scheduler_tick(), когда процесс истрачивает свой квант времени, и функцией >try_to_wake_up(), когда процесс с приоритетом более высоким, чем у текущего процесса, возвращается к выполнению. Ядро проверяет значение этого флага, и если он установлен, то вызывается функция >schedule() для переключения на новый процесс. Этот флаг является сообщением ядру о том, что планировщик должен быть активизирован по возможности раньше, потому что другой процесс должен начать выполнение.


Таблица 4.2. Функции для управления флагом need_resched

ФункцияНазначение
>set_tsk_need_resched(task)Установить флаг >need_resched для данного процесса
>clear_tsk_need_resched(task)Очистить флаг >need_resched для данного процесса
>need_resched()Проверить значение флага >need_resched для данного процесса. Возвращается значение >true, если этот флаг установлен, и >false, если не установлен

Во время переключения в пространство пользователи или при возврате из прерывания, значение флага >need_resched проверяется. Если он установлен, то ядро активизирует планировщик перед тем, как продолжить работу.

Этот флаг не является глобальной переменной, так как обращение к дескриптору процесса получается более быстрым, чем обращение к глобальным данным (из-за скорости обращения к переменной >current и потому, что соответствующие данные могут находиться в кэше). Исторически, этот флаг был глобальным в ядрах до серии 2.2. В ядрах серий 2.2 и 2.4 этот флаг принадлежал структуре