Статическая и глобальная переменная в памяти - PullRequest
3 голосов
/ 11 марта 2010
  1. Являются ли статические переменные, хранящиеся в самом стеке, похожими на глобальные переменные?Если да, то как они защищены, чтобы разрешить доступ только локальным классам?

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

Ответы [ 4 ]

3 голосов
/ 11 марта 2010

Переменные, хранящиеся в стеке, носят временный характер. Они принадлежат функции и т. Д., И когда функция возвращается и соответствующий кадр стека удаляется, переменные стека исчезают вместе с ней. Поскольку глобальные переменные предназначены для повсеместного доступа, они не должны выходить из контекста и поэтому хранятся в куче (или в специальном разделе данных двоичного файла), а не в стеке. То же самое касается static переменных; поскольку они должны хранить свое значение между вызовами функции, они не могут исчезнуть при возврате функции, поэтому они не могут быть размещены в стеке.

Что касается защиты static переменных, IIRC это в основном выполняется компилятором. Даже если переменная находится в куче, ваш компилятор знает ограниченный контекст, в котором эта переменная является допустимой, и любая попытка доступа к static извне этого контекста приведет к «неизвестному идентификатору» или аналогичной ошибке. Единственный другой способ неверного доступа к переменной кучи - это если вы знаете адрес static и слепо отмените ссылку на него. Это должно привести к ошибке доступа к памяти во время выполнения.

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

3 голосов
/ 11 марта 2010

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

При использовании static / globals в многопоточной ситуации возникает проблема, заключающаяся в том, что если один поток изменяет переменную в то же время, когда другой пытается прочитать ее (только для одного примера), получаемые данные могут быть неверными данными.

2 голосов
/ 11 марта 2010

Являются ли статические переменные, хранящиеся в самом стеке, похожими на глобальные переменные? Если да, то как они защищены, чтобы разрешить доступ только локальным классам?

Обычно они хранятся в памяти вместе с глобальными. однако видимость имен переменных ограничивает доступ.

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

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

1 голос
/ 11 марта 2010

Являются ли статические переменные, хранящиеся в самом стеке, похожими на глобальные переменные? Если да, то как они защищены, чтобы разрешить доступ только локальным классам?

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

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

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

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...