Блокирующие переменные
Для синхронизации потоков одного процесса используют глобальные блокирующие переменные и все потоки процесса имеют к ним прямой доступ, не обращаясь к системным вызовам ОС.
Рисунок 5.3 - Реализация критических секций с использованием блокирующих переменных
На рисунке 5.3 показан фрагмент алгоритма потока, использующего для реализации взаимного исключения доступа к критическим данным D блокирующую переменную F(D). Если переменная F(D) установлена в 0, то данные заняты и проверка циклически повторяется. Если же данные свободны (F(D) = 1), то значение переменной F(D) устанавливается в 0 и поток входит в критическую секцию. После того как поток выполнит все действия с данными D, значение переменной F(D) снова устанавливается равным 1.
Блокирующие переменные могут использоваться и при доступе к разделяемым ресурсам любого вида.
Если все потоки написаны с учетом вышеописанных соглашений, то взаимное исключение гарантируется. При этом потоки могут быть прерваны операционной системой в любой момент и в любом месте, в том числе в критической секции.
Одно ограничение на прерывания - нельзя прерывать поток между выполнением операций проверки и установки блокирующей переменной.
Во избежание таких ситуаций в системе команд предусмотрена единая, неделимая команда анализа и присвоения значения логической переменной (например, команды ВТС, BTR и BTS процессора Pentium). При отсутствии такой команды в процессоре соответствующие действия должны реализовываться специальными системными примитивами, которые бы запрещали прерывания на протяжении всей операции проверки и установки.
Реализация взаимного исключения описанным выше способом имеет существенный недостаток: в течение времени, когда один поток находится в критической секции, другой поток, которому требуется тот же ресурс, получив доступ к процессору, будет непрерывно опрашивать блокирующую переменную, бесполезно тратя выделяемое ему процессорное время. Для устранения этого недостатка во многих ОС предусматриваются специальные системные вызовы для работы с критическими секциями (MS Windows – EnterCriticalSection, LeaveCriticalSection).