Заборы исполнения и памяти - PullRequest
10 голосов
/ 08 сентября 2011

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

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

Теперь говорят, что для использования многоядерных платформ требуются ограждения памяти, поскольку из-за выполнения Out of Order здесь может быть напечатано неправильное значение x .

Processor #1:
 while f == 0
  ;
 print x; // x might not be 42 here

Processor #2:
 x = 42;
 // Memory fence required here
 f = 1

Теперь мой вопрос заключается в том, что процессоры Out of Order (ядра в случае многоядерных процессоров, я полагаю) всегда удаляют результаты In-Order, тогда зачем нужны заборы памяти. Разве ядра многоядерного процессора не видят результаты, удаленные только из других ядер, или они также видят результаты, которые находятся в полете?

Я имею в виду в примере, который я привел выше, когда Процессор 2 в конечном итоге выведет из строя результаты, результат x должен предшествовать f , верно? Я знаю, что во время выполнения заказа он мог изменить f до x , но, должно быть, он не удалил его до x , верно?

Теперь, когда в порядке упорядочения результатов и механизма согласованности кэша вам понадобится забор памяти в x86?

Ответы [ 3 ]

15 голосов
/ 08 сентября 2011

Этот туториал объясняет проблемы: http://www.hpl.hp.com/techreports/Compaq-DEC/WRL-95-7.pdf

FWIW, где проблемы с упорядочением памяти возникают на современных процессорах x86, причина в том, что, хотя модель согласованности памяти x86 предлагает довольно сильную согласованность, для обработки согласованности чтения после записи необходимы явные барьеры. Это связано с тем, что называется «буфер хранилища».

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

store x
load y

тогда на процессорной шине это можно увидеть как

load y
store x

Причиной такого поведения является вышеупомянутый буфер хранилища, который является небольшим буфером для записей перед их выходом на системную шину. Задержка загрузки является, OTOH, критической проблемой для производительности, и, следовательно, нагрузкам разрешено «переходить в очередь».

См. Раздел 8.2 в http://download.intel.com/design/processor/manuals/253668.pdf

7 голосов
/ 08 сентября 2011

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

Если вы не установите ограничение памяти, ядра могут работать с неверными данными, это особенно заметно в сценарии, где несколько ядер будут работать с одинаковыми наборами данных. В этом случае вы можете убедиться, что после того, как CPU 0 выполнил какое-то действие, все изменения, внесенные в набор данных, теперь видны всем другим ядрам, которые затем могут работать с актуальной информацией.

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

Если ядро ​​начнет работать с устаревшими данными в наборе данных, как оно сможет получить правильные результаты? Неважно, должен ли конечный результат быть представлен так, как если бы все было сделано в правильном порядке.

Ключ находится в буфере хранилища, который находится между кешем и процессором, и делает это:

Хранить буфер, невидимый для удаленных процессоров

Буфер хранилища позволяет сохранять записи в память и / или в кеши оптимизировать межсоединения

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

EDIT:

Для кода, который вы использовали в качестве примера, Википедия говорит следующее:

Барьер памяти может быть вставлен перед присвоением процессору № 2 функции f чтобы убедиться, что новое значение х видно для других процессоров в или до изменения значения е.

2 голосов
/ 27 декабря 2017

Просто чтобы четко указать, что подразумевается в предыдущих ответах, это правильно, но отличается от обращений к памяти:

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

Удаление команды отдельно от выполнения доступа к памяти, доступ к памяти может завершиться в разное время, чем удаление инструкции.

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

(На x86 и ARM, я думаю, что только хранилища подвержены этому, но, например, Alpha может загрузить старое значение из памяти.x86 SSE2 имеет инструкции с более слабыми гарантиями, чем обычное поведение x86.

PS.По памяти заброшенный Sparc ROCK мог фактически выйти из строя, он потратил энергию и транзисторы, определяя, когда это безвредно.От него отказались из-за энергопотребления и количества транзисторов ... Я не верю, что какой-либо ЦП общего назначения был куплен на рынке с вышедшим из строя выводом из эксплуатации.

...