Монітор (синхронізація)
Монітор — в мовах програмування, це високорівнева конструкція для отримання ексклюзивного доступу до спільних ресурсів.
Монітор реалізується за допомогою м'ютекса та умовних змінних.
Монітор був винайдений П.Б. Хансеном[1] та Тоні Гоаром[2] та вперше був застосований в мові Concurrent Pascal.
М'ютекс
Монітор гарантує ексклюзивний доступ до класу, об'єкта чи модуля за допомогою використання м'ютекса.
Приклад об'єкта, що гарантує безпечний доступ до банківського рахунку:
monitor class Account {
private int balance := 0
invariant balance >= 0
public method boolean withdraw(int amount)
precondition amount >= 0
{
if balance < amount then return false
else { balance := balance - amount ; return true }
}
public method deposit(int amount)
precondition amount >= 0
{
balance := balance + amount
}
}
Під час виконання потоком метода такого об'єкта, кажуть, що потік займає (чи заблоковує) об'єкт, утримаючи його м'ютекс (lock). В кожен конкретний момент часу не більше одного потоку може виконувати код цього об'єкта.
monitor
є синтаксичним цукром для того, щоб не писати код захвату/вивільнення м'ютекса.
Умовні змінні
Якщо метод монітора має дочекатись деякої умови, що встановлюється методом того самого монітора в іншому потоці, то цей метод повинен:
- тимчасово звільнити м'ютекс та очікувати (призупинити своє виконання),
- після зміни умови отримати м'ютекс назад та бути оповіщеним (пробудженим).
Така функціональність реалізується за допомогою змінних умови (умовна змінна).
Технічно, умовна змінна є списком потоків, що очікують на дану умову. Поки потік очікує на умовну змінну, він не може зайняти монітор.
Єдиними операціями можливими над умовною змінною є: очікування та оповіщення.
Блокуюча умовна змінна — рання реалізація (реалізація Хоара), що при оповіщенні умовної змінної, негайно активізує очікуючий потік та віддає йому м'ютекс. Ця реалізація технічно складна, і її єдина перевага в тому, що оповіщений потік може бути впевненим, що умова ще чинна.
Неблокуюча умовна змінна — більш пізня реалізація (реалізація Mesa) дозволяє потоку, що оповіщує завершити метод монітора, а аж потім пробудити очікуючий потік. Це реалізація більш проста, але вона не гарантує чинності умови в момент пробудження потоку, оскільки умова могла після першої зміни знову змінитись.
Тому, в коді очікування потрібно писати while test then wait(cv)
замість if test do wait(cv)
.
Поширення
Монітори підтримують мови програмування:
Примітки
- Brinch Hansen, Per (1973). 7.2 Class Concept. Operating System Principles. Prentice Hall. ISBN 0-13-637843-9.
- Hoare, C. A. R. (October 1974). Monitors: an operating system structuring concept. Comm. ACM 17 (10): 549–557. doi:10.1145/355620.361161.
Посилання
- Java Monitors (lucid explanation)
- "Strategies for Implementing POSIX Condition Variables on Win32" by Douglas C. Schmidt and Irfan Pyarali
- http://en.cppreference.com/w/cpp/thread/condition_variable
- http://msdn.microsoft.com/en-us/library/system.threading.monitor.aspx
- http://msdn.microsoft.com/en-us/library/ms682052.aspx