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

Насколько я знаю, и компилятор, и процессор могут выполнять переупорядочение команд. Под "выполнением ЦП" я подразумеваю, что меня не волнует переупорядочение команд, выполняемое компилятором, и переупорядочение, вызванное буфером хранилища и кэшем ЦП. Для переупорядочения, вызванного Store Buffer и CPU Cache, который обсуждался в этой статье, я уже понял, как барьер памяти препятствует такому переупорядочению (переупорядочению памяти).

Что меня волнует, так это переупорядочение:

Исходный код:

data=1; //statement1
ready=true;//statement2

Но, ThreadA, запущенный на CPU0, выполняет приведенный выше код в следующем порядке:

ready=true;//statement2
data=1; //statement1

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

Новый исходный код:

data=1; //statement1
smp_wb();//Insert a write barrier here!
ready=true;//statement2

Итак, возникает мой вопрос: как барьер памяти препятствует переупорядочению команд здесь?

1 ответ

Решение

@ Цыварев правильный, он специфичен для процессора (или семейства процессоров). Например, в ARM DMB(барьер памяти) вызывает остановку конвейера ЦП, чтобы обеспечить упорядочение (предотвращает переупорядочение), как сказано в его документации:

На рисунке 1 показана инструкция DMB, используемая для обеспечения упорядочения памяти путем остановки конвейера.

Другие вопросы по тегам