Должен ли я блокировать переменную в одном потоке, если мне нужно только ее значение в других потоках, и почему это работает, если я этого не делаю? - PullRequest
5 голосов
/ 04 августа 2011

Мне известен этот вопрос , но я считаю, что мои опасения очень разные.

Я недавно создал приложение SDL, используя потоки и OpenGL. У меня есть один поток, работающий в цикле, который постоянно обновляет состояние объектов, которые я рисую на экране. Состояния очень просты, это просто логический массив (когда значение массива истинно, я рисую его, когда оно ложно, нет).

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

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

  • Это случайно или по какой-то причине нарушения доступа к памяти не происходят?
  • Если допустимо изменение состояния переменной непосредственно перед, во время или сразу после использования значения, стоит ли беспокоиться об использовании блокировки мьютекса?

Спасибо за вашу помощь.


Редактировать: Дополнительная информация - массив создается динамически, но когда он создается / удаляется, я использую мьютекс (я полагал, что доступ к удаленной памяти не будет любезным: P).

Ответы [ 2 ]

8 голосов
/ 04 августа 2011

Теоретически, совершенно недопустимо (неопределенное поведение) доступ к памяти, подобной этой, без некоторой синхронизации.

На практике это в меру безопасно, если:

  1. Только один потокпишет, а остальные все читают.
  2. Вам все равно, не увидят ли читатели некоторые изменения, сделанные до некоторого времени позже (возможно, намного позже , чем фактическое время, когда онинаписано.
  3. Вам все равно, увидят ли читатели неупорядоченные изменения, т.е. они увидят некоторые изменения, которые были сделаны позже, не видя других изменений, которые были сделаны ранее.

Проблемы 2 и 3 не являются проблемой на x86, но могут возникать практически на любой другой реальной машине с многоядерными процессорами или SMP. Вы можете смягчить их с помощью некоторого специфичного для машины asm (иливстроенные функции компилятора) для вставки барьеров памяти в соответствующих точках.

1 голос
/ 04 августа 2011

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

...