Я нашел эту проблему в очень большом приложении, сделал из него SSCCE. Я не знаю, имеет ли код неопределенное поведение или -O2
нарушает его.
При компиляции с gcc a.c -o a.exe -O2 -Wall -Wextra -Werror
выводится 5.
Но он печатает 25 при компиляции без -O2
(например, -O1
) или раскомментирования одной из двух закомментированных строк (предотвращает встраивание).
#include <stdio.h>
#include <stdlib.h>
// __attribute__((noinline))
int f(int* todos, int input) {
int* cur = todos-1; // fixes the ++ at the beginning of the loop
int result = input;
while(1) {
cur++;
int ch = *cur;
// printf("(%i)\n", ch);
switch(ch) {
case 0:;
goto end;
case 1:;
result = result*result;
break;
}
}
end:
return result;
}
int main() {
int todos[] = { 1, 0}; // 1:square, 0:end
int input = 5;
int result = f(todos, input);
printf("=%i\n", result);
printf("end\n");
return 0;
}
Является ли опция GCC -O2
нарушением этой небольшой программы или у меня где-то есть неопределенное поведение?
todos - 1
и использоватьint ch = *cur++;
вместо увеличения перед разыменованием. - person asveikau   schedule 15.05.2014ch
не инициализирован.. не могу понять, почему - person Mark Nunberg   schedule 15.05.2014todo
как{ -1, 1, 0 }
, а затем передаю&todos[1]
вf()
, программа дает желаемый результат - person Mark Nunberg   schedule 15.05.2014todos-1
даже при том, что он не разыменовывается? интересно! - person Bernd Elkemann   schedule 15.05.2014