Добавил:
Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Учебное пособие 700363.doc
Скачиваний:
17
Добавлен:
01.05.2022
Размер:
3.69 Mб
Скачать

Выход из критической секции

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

Системный вызов для освобождения объекта синхронизации может быть оформлен, например, в виде следующей функции.

void ReleaseSyncObject(int id).

Здесь id – идентификатор требуемого объекта синхронизации.

Если в системе присутствуют процессы, приостановленные в ожидании данного объекта синхронизации, то их выполнение возобновляется.

Системный вызов для освобождения объекта синхронизации может быть реализован по алгоритму, показанному на рис.15.

Рис.15. Алгоритм освобождения объекта синхронизации

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

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

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

Замечания по реализации примитивов синхронизации

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

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

На однопроцессорной машине достаточно просто запретить прерывания на время работы примитива синхронизации, и это будет гарантировать отсутствие конфликтов при работе примитивов синхронизации.

На многопроцессорной же машине всегда существует вероятность одновременного обращения к объекту синхронизации из программ, выполняющихся на различных процессорах, поэтому для реализации взаимоисключения при работе примитивов синхронизации необходимо дополнительно к запрету прерываний использовать блокировки на основе цикла ожидания (spin-блокировки). Тогда, при возникновении конфликта между процессорами, один из них будет выполнять цикл ожидания до освобождения критического ресурса.

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