Рассмотрим этот код C:
extern volatile int hardware_reg;
void f(const void *src, size_t len)
{
void *dst = <something>;
hardware_reg = 1;
memcpy(dst, src, len);
hardware_reg = 0;
}
Вызов memcpy()
должен выполняться между двумя назначениями. В общем, поскольку компилятор, вероятно, не знает, что вызовет вызываемая функция, он не может изменить порядок вызова функции, которая должна быть до или после назначений. Однако в этом случае компилятор знает, что будет делать функция (и может даже вставить встроенный встроенный заменитель), и он может вывести, что memcpy()
никогда не сможет получить доступ к hardware_reg
. Здесь мне кажется, что компилятор не видит проблем при перемещении вызова memcpy()
, если он этого захочет.
Итак, вопрос: достаточно ли одного вызова функции, чтобы выпустить барьер памяти, который предотвратил бы переупорядочение, или, в противном случае, явный барьер памяти, необходимый в этом случае до и после вызова memcpy()
?
Пожалуйста, поправьте меня, если я не понимаю вещи.