Мы знаем, что логический оператор AND (&&
) гарантирует оценку слева направо.Может ли оптимизатор компилятора C нарушить короткое замыкание и изменить порядок доступа к памяти для операндов в логическом выражении?
Но мне интересно, если оптимизатор компилятора может когда-либо реорганизовать инструкции доступа к памяти для *a
и b->foo
в следующем коде, т.е. оптимизатора пишет инструкции, которые пытаются получить доступ *b
перед обращением *a
.
(Рассмотрим как a
и b
быть указатели на области памяти в куче.)
if (*a && b->foo) {
/* do something */
}
Можно подумать, что &&
вызывает точку последовательности, так что компилятор должен испускать инструкции для доступа *a
перед обращением *b
но после прочтения принятого ответа на https://stackoverflow.com/a/14983432/1175080, я не уверен. Если вы посмотрите на этот ответ, между операторами есть полуколоны, и они также устанавливают точки последовательности, и поэтому они также должны препятствовать переупорядочению, но ответ там, кажется, указывает, что им нужен уровень памяти уровня компилятора, несмотря на наличие точек с запятой.
Я имею в виду, если вы утверждаете, что &&
устанавливает точку последовательности, то это верно для точек с запятой в коде на https://stackoverflow.com/a/14983432/1175080. Тогда почему в этом коде требуется защитный барьер на уровне компилятора?
и в каком сценарии это происходит _may_? –
Да. См. Правило [as-if] (https://en.wikipedia.org/wiki/As-if_rule). – AlexD
Я думал, что '&&' вызвало точку последовательности. Таким образом, выборка/оценка 'b' должна быть' * a' ложной. Hmm @ AlexD as-if берет на себя внимание. – chux