Jump to content

Блокировка чтения и записи

В информатике читатель -писатель ( блокировка одного писателя , [1] замок многоридерный , [2] замок нажимной , [3] или блокировка MRSW ) — примитив синхронизации , решающий одну из проблем чтения-записи . Блокировка RW обеспечивает одновременный доступ для операций только для чтения, тогда как операции записи требуют монопольного доступа. Это означает, что несколько потоков могут читать данные параллельно, но монопольная блокировка для записи или изменения данных необходима . Когда писатель записывает данные, все остальные записи и читатели будут заблокированы до тех пор, пока писатель не завершит запись. Обычное использование может заключаться в управлении доступом к структуре данных в памяти, которая не может обновляться атомарно и является недопустимой (и не должна быть прочитана другим потоком) до завершения обновления.

Блокировки чтения-записи обычно создаются поверх мьютексов и условных переменных или поверх семафоров .

Модернизируемый замок RW

[ редактировать ]

Некоторые блокировки RW позволяют автоматически обновлять блокировку из режима чтения в режим записи, а также переводить блокировку из режима записи в режим чтения. [1] Обновление блокировки из режима чтения в режим записи подвержено взаимоблокировкам, поскольку всякий раз, когда два потока, удерживающие блокировки чтения, оба пытаются перейти на блокировки записи, создается взаимоблокировка, которую может сломать только один из потоков, освобождающий ее. блокировка считывателя. Взаимной блокировки можно избежать, разрешив только одному потоку получить блокировку в «режиме чтения с намерением перейти на запись», в то время как в режиме записи нет потоков и, возможно, ненулевых потоков в режиме чтения.

Приоритетная политика

[ редактировать ]

Блокировки RW могут быть спроектированы с использованием различных политик приоритета для доступа чтения и записи. Блокировка может быть спроектирована так, чтобы всегда отдавать приоритет читателям ( предпочтение чтения ), всегда отдавать приоритет записи ( предпочтение записи ), или быть неуказанной в отношении приоритета. Эти политики приводят к различным компромиссам в отношении параллелизма и голодания .

  • Блокировки RW с предпочтением чтения обеспечивают максимальный параллелизм, но могут привести к нехватке записи, если конкуренция высока. Это связано с тем, что потоки записи не смогут получить блокировку, пока ее удерживает хотя бы один поток чтения. Поскольку несколько потоков чтения могут удерживать блокировку одновременно, это означает, что поток записи может продолжать ждать блокировки, в то время как новые потоки чтения могут получить блокировку, даже до такой степени, что писатель все еще может ждать после всех читателей. которые удерживали замок, когда он впервые попытался его захватить, отпустили замок. Приоритет для читателей может быть слабым , как только что описано, или сильным , что означает, что всякий раз, когда писатель снимает блокировку, любые блокирующие читатели всегда получают ее следующей. [4] : 76 
  • Блокировки RW с предпочтением записи позволяют избежать проблемы нехватки средств записи, не позволяя новым читателям получить блокировку, если в очереди находится записывающее устройство, ожидающее блокировки; писатель получит блокировку, как только все читатели, которые уже удерживали блокировку, завершат работу. [5] Обратной стороной является то, что блокировки, предпочитающие запись, допускают меньший параллелизм при наличии потоков записи по сравнению с блокировками RW, предпочитающими чтение. Кроме того, блокировка менее производительна, поскольку каждая операция по снятию или снятию блокировки для чтения или записи является более сложной и внутренне требует захвата и освобождения двух мьютексов вместо одного. [ нужна ссылка ] Этот вариант иногда также называют блокировкой чтения-писателя с предвзятостью к записи. [6]
  • Блокировки RW с неуказанным приоритетом не дают никаких гарантий в отношении доступа для чтения и записи. Неопределенный приоритет в некоторых ситуациях может быть предпочтительнее, если он обеспечивает более эффективную реализацию. [ нужна ссылка ]

Выполнение

[ редактировать ]

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

Использование двух мьютексов

[ редактировать ]

Рейнал демонстрирует, как реализовать блокировку чтения/записи с использованием двух мьютексов и одного целочисленного счетчика. Счетчик b отслеживает количество блокирующих читателей. Один мьютекс r защищает b и используется только читателями; другой, g (от слова «глобальный»), обеспечивает взаимное исключение авторов. Для этого необходимо, чтобы мьютекс, захваченный одним потоком, мог быть освобожден другим. Ниже приведен псевдокод для операций:

Инициализировать

  • Установите b на 0 .
  • р разблокирован.
  • г разблокирован.

Начать читать

  • Замок р .
  • Приращение б .
  • Если b = 1 , заблокируйте g .
  • Разблокировать р .

Завершить чтение

  • Замок р .
  • Декремент б .
  • Если b = 0 , разблокируйте g .
  • Разблокировать р .

Начать писать

  • Замок г.

Конец записи

  • Разблокировать г.

Эта реализация предпочитает чтение. [4] : 76 

Использование условной переменной и мьютекса

[ редактировать ]

В качестве альтернативы блокировка RW может быть реализована с помощью условной переменной , cond обычной блокировки (мьютекса) g и различных счетчиков и флагов, описывающих потоки, которые в данный момент активны или ожидают. [7] [8] [9] Для блокировки RW с предпочтением записи можно использовать два целочисленных счетчика и один логический флаг:

  • num_readers_active : количество читателей, получивших блокировку (целое число)
  • num_writers_waiting : количество записывающих устройств, ожидающих доступа (целое число)
  • write_active : получил ли писатель блокировку (логическое значение).

Первоначально num_readers_active и num_writers_waiting равны нулю, а write_active имеет значение false.

Операции блокировки и освобождения могут быть реализованы как

Начать читать

  • Замок г
  • Пока num_writers_waiting > 0 или write_active :
    • ожидания условия , г [а]
  • Увеличение num_readers_active
  • Разблокировать г.

Завершить чтение

  • Замок г
  • Уменьшить num_readers_active
  • Если num_readers_active = 0 :
    • уведомления Условие (трансляция)
  • Разблокировать г.

Начать писать

  • Замок г
  • Увеличение num_writers_waiting
  • Пока num_readers_active > 0 или write_active имеет значение true :
    • ожидания условия , г
  • Уменьшить num_writers_waiting
  • Установите write_active для значение true
  • Разблокировать г.

Конец записи

  • Замок г
  • Установите write_active для значение false
  • уведомления Условие (трансляция)
  • Разблокировать г.

Поддержка языков программирования

[ редактировать ]

Альтернативы

[ редактировать ]

Алгоритм чтения-копирования-обновления (RCU) является одним из решений проблемы чтения-писателя. RCU не требует ожидания для читателей. Ядро Linux реализует специальное решение для немногих авторов, называемое seqlock .

См. также

[ редактировать ]

Примечания

[ редактировать ]
  1. ^ Это стандартная операция «ожидания» для условных переменных, которая, помимо других действий, освобождает мьютекс g .
  1. ^ Гамильтон, Дуг (21 апреля 1995 г.). «Предложения по блокировке с несколькими устройствами чтения и одной записи?» . Группа новостей : comp.os.ms-windows.nt.misc . Usenet:   [электронная почта защищена] . Проверено 8 октября 2010 г.
  2. ^ «Практическая свобода блокировки» Кейра Фрейзера, 2004 г.
  3. ^ «Нажимные замки – что это такое?» . Блог Ntdebugging . Блоги MSDN. 2 сентября 2009 года . Проверено 11 мая 2017 г.
  4. ^ Перейти обратно: а б Рейналь, Мишель (2012). Параллельное программирование: алгоритмы, принципы и основы . Спрингер.
  5. ^ Стивенс, В. Ричард ; Раго, Стивен А. (2013). Расширенное программирование в среде UNIX . Аддисон-Уэсли. п. 409.
  6. ^ Перейти обратно: а б java.util.concurrent.locks.ReentrantReadWriteLock Реализация блокировки чтения и записи Java предлагает «честный» режим.
  7. ^ Херлихи, Морис; Шавит, Нир (2012). Искусство многопроцессорного программирования . Эльзевир. стр. 184–185.
  8. ^ Николс, Брэдфорд; Баттлар, Дик; Фаррелл, Жаклин (1996). Программирование PThreads: стандарт POSIX для лучшей многопроцессорной обработки . О'Рейли. стр. 84–89 . ISBN  9781565921153 .
  9. ^ Бутенхоф, Дэвид Р. (1997). Программирование с использованием потоков POSIX . Аддисон-Уэсли. стр. 253–266.
  10. ^ «Базовые спецификации открытой группы, выпуск 6, IEEE Std 1003.1, издание 2004 г.: pthread_rwlock_destroy» . IEEE и Открытая группа . Проверено 14 мая 2011 г.
  11. ^ java.util.concurrent.locks.ReadWriteLock
  12. ^ «Класс ReaderWriteLockSlim (System.Threading)» . Корпорация Майкрософт . Проверено 14 мая 2011 г.
  13. ^ «Новый принятый документ: N3659, Совместная блокировка в C++ — Говард Хиннант, Детлеф Фоллманн, Ханс Бём» . Стандартная основа C++.
  14. ^ Энтони Уильямс. «Синхронизация — Boost 1.52.0» . Проверено 31 января 2012 г.
  15. ^ Алессандрини, Виктор (2015). Программирование приложений с общей памятью: концепции и стратегии программирования многоядерных приложений . Морган Кауфманн.
  16. ^ «Язык программирования Go – синхронизация пакетов» . Проверено 30 мая 2015 г.
  17. ^ «Синхронизация чтения и записи для многопроцессорных систем реального времени с общей памятью» (PDF) .
  18. ^ "std::sync::RwLock — Rust" . Проверено 26 октября 2019 г.
  19. ^ «Блокировка чтения/записи для Twisted» . Гитхаб . Проверено 28 сентября 2016 г.
  20. ^ «Примитивы синхронизации в ядре Linux: семафоры чтения/записи» . Линукс изнутри . Проверено 8 июня 2023 г.
Arc.Ask3.Ru: конец переведенного документа.
Arc.Ask3.Ru
Номер скриншота №: 9a10e49182b65058045fcdd8106529dc__1686215640
URL1:https://arc.ask3.ru/arc/aa/9a/dc/9a10e49182b65058045fcdd8106529dc.html
Заголовок, (Title) документа по адресу, URL1:
Readers–writer lock - Wikipedia
Данный printscreen веб страницы (снимок веб страницы, скриншот веб страницы), визуально-программная копия документа расположенного по адресу URL1 и сохраненная в файл, имеет: квалифицированную, усовершенствованную (подтверждены: метки времени, валидность сертификата), открепленную ЭЦП (приложена к данному файлу), что может быть использовано для подтверждения содержания и факта существования документа в этот момент времени. Права на данный скриншот принадлежат администрации Ask3.ru, использование в качестве доказательства только с письменного разрешения правообладателя скриншота. Администрация Ask3.ru не несет ответственности за информацию размещенную на данном скриншоте. Права на прочие зарегистрированные элементы любого права, изображенные на снимках принадлежат их владельцам. Качество перевода предоставляется как есть. Любые претензии, иски не могут быть предъявлены. Если вы не согласны с любым пунктом перечисленным выше, вы не можете использовать данный сайт и информация размещенную на нем (сайте/странице), немедленно покиньте данный сайт. В случае нарушения любого пункта перечисленного выше, штраф 55! (Пятьдесят пять факториал, Денежную единицу (имеющую самостоятельную стоимость) можете выбрать самостоятельно, выплаичвается товарами в течение 7 дней с момента нарушения.)