Вопрос

Какова модель памяти для параллелизма в C++03?

(И изменяет ли C++11 модель памяти для лучшей поддержки параллелизма?)

Это было полезно?

Решение

Модель памяти C++ — это спецификация того, когда и почему физическая память читается/записывается по отношению к коду C++.

До следующего стандарта C++ модель памяти C++ такая же, как и в C.Ожидается, что в стандарт C++0x будет включена правильная модель памяти для многопоточности (см. здесь), и, возможно, он станет частью следующей версии стандарта C, C1X.Текущий элемент элементарный:

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

Итак, текущее состояние:Операции с памятью C++ указываются только в том случае, если у вас есть 1 процесс с его основным потоком и вы не пишете код, который зависит от определенного порядка чтения/записи переменных и все.По сути, это означает, что, если не считать традиционной программы hello world, вы облажались.

Конечно, вам будет предложено добавить это «Сегодня это работает на моей машине, возможно, ты прав».Правильным предложением будет «Сегодня он работает на моей машине с этой конкретной комбинацией оборудования, операционной системы (библиотеки потоков) и компилятора, которые знают друг друга достаточно, чтобы реализовать что-то, что в некоторой степени работает, но, вероятно, в какой-то момент сломается».

Хорошо, хорошо, это немного жестко, но, черт возьми, даже Херб Саттер признает это (просто прочитайте вступление), и он говорит обо всех версиях одного из самых распространенных наборов инструментов C/C++ до 2007 года...

Комитет по стандартизации C++ пытается придумать что-то, что решит все эти проблемы, но при этом будет менее ограничивающим (и, следовательно, более производительным), чем модель памяти Java.

Ганс Бём собрал здесь некоторые ссылки на статьи по этому вопросу, как академические, так и комитеты C++.

Другие советы

Видя некоторые другие ответы, кажется, что многие программисты на C ++ даже не знают, что такое "модель памяти". вы спрашиваете о средствах.

Вопрос касается модели памяти в том смысле: какие гарантии (если таковые имеются) существуют в отношении переупорядочения записи / чтения (что может произойти на стороне компилятора или на этапе выполнения)? Этот вопрос очень важен для многопоточного программирования, так как без таких правил написание правильных многопоточных программ невозможно, и несколько удивительная истина заключается в том, что при нынешнем отсутствии явной модели памяти многие многопоточные программы работают более или менее «по счастливой случайности». - чаще всего благодаря компиляторам, предполагающим наложение указателей на вызовы функций. - см. Потоки не могут быть реализованы в виде библиотеки

В текущем C ++ нет стандартной модели памяти. Некоторые компиляторы определяют модель памяти для изменчивых переменных, но это нестандартно. C ++ 0x определяет новый «атомарный» Примитивы для этой цели. Исчерпывающую отправную точку, чтобы проверить, что в последнее время статус, можно найти на Потоки и модель памяти для C ++

Важными ссылками также являются модель памяти для параллелизма , атомные типы и C ++ Упорядочение зависимости данных: модель атома и памяти Стандартные предложения.

К сожалению, в C++ нет «стандартной модели памяти», такой как в Java.Фактическая реализация остается на усмотрение компилятора, библиотек времени выполнения и процессоров.

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

А как насчет проверки документов на веб-сайте комитета по стандартизации C++:

?

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

http://rsim.cs.uiuc.edu/~sadve /Publications/computer96.pdf

Краткий ответ: нет ни одного

Длинный ответ: C ++ не имеет управляемой памяти, вы должны выделить ее и освободить самостоятельно. Умные классы указателей могут сделать это менее обременительным. Если вы забудете освободить выделенную память, это утечка памяти и ошибка. Если вы попытаетесь использовать память после ее освобождения или попытаетесь освободить память более одного раза, это тоже неприятные ошибки.

Что касается низкоуровневых деталей, C ++ не указывает это - это зависит от аппаратного обеспечения. Доступ к памяти осуществляется через указатели, которые содержат какой-то адрес памяти. Адреса памяти могут быть физическими или виртуальными. Вы увидите физические адреса, только если работаете над ядром операционной системы или читаете старый код DOS, работающий в реальном режиме. Подробнее читайте в виртуальной памяти , там много хороших ресурсов.

Архитектура x86 также позволяет адресовать память с использованием дескрипторов сегментов. Это целый набор «червей», который на самом деле не использовался со времен Win16, и если вам повезет, вам никогда не придется иметь с этим дело.

Вкратце, модель памяти C++ состоит из...

  • Стек, который растет вниз — то есть, когда вы нажимаете кадр стека, указатель стека имеет значение меньшее, чем было

  • Куча, которая растет вверх, то есть конечный адрес вновь выделенной памяти больше, чем был до памяти.Вы выделяете память в куче, используя malloc() или new.Если в куче недостаточно памяти, то malloc (или new) вызывает системную функцию brk() sbrk(), чтобы увеличить размер кучи.Если вызов brk() или sbrk() завершится неудачно, то malloc или new завершится с ошибкой с исключением нехватки памяти.

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

  • Распределитель памяти malloc, который выделяет память в виде 8-битных байтов.Команда New также выделяет память, но объем выделяемой памяти зависит от размера нового объекта.

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

Программа может иметь другие разделы специального назначения под текстом.

Вы можете увидеть, как программа организована статически (до ее загрузки), используя objdump в системах Linux.

Я заметил, что, хотя вы не упомянули об этом в своем вопросе, «параллелизм» — одно из ключевых слов, которые вы присвоили этому вопросу.Системы потоков выделяют дополнительное пространство в куче для каждого потока, а затем управляют указателем стека для переключения между потоками.

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

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top