RobertoCesco <ilcescofabbro@xxxxxxxx> writes: > This program has a strange behaviour, probably due to FP optimizations using > the -O1 or -O2 or -O3 (I can resolve it with the GCC compilation flag > -ffloat-store). > It should produce the same output twice (because it prints the same variable > in 2 consecutive lines), but it does not; there are some errors on the last > digits. Someone can explain me what happen? > > Source: > > http://old.nabble.com/file/p33858981/bug.c bug.c > > > Compile: > > gcc -O3 -o bug bug.c > > Output: > > 132.316432 132.316437 > 108.085940 108.085938 > 134.695360 134.695358 > 123.992232 123.992233 > > > I tested it with the following systems: > > Intel i5, Ubuntu Linaro, kernel 3.0.0-19-generic, GCC 4.6.1-9ubuntu3 > Intel i7, Ubuntu Linaro, kernel 2.6.38-15-generic, GCC 4.5.2-8ubuntu4 You didn't say, but you are presumably using an x86 in 32-bit mode. In C, the float type is promoted to double when making a function call. Your first call to printf takes the 80-bit 387 register, stores it to the stack as a 64-bit double, and calls printf. But before calling printf the 80-bit register is stored on the stack as a 32-bit float, since that is the variable's type. For the second call to printf the 32-bit float is loaded from the stack into a 80-bit register, then stored to the stack as a 64-bit double to pass to printf. So the problem is the value is rounded one way when stored as a 64-bit value and rounded a different way when stored as a 32-bit value. That is what you are seeing. The fix is, as you discovered, to use -ffloat-store. Or, if using GCC 4.5 or newer, to use -fexcess-precision=standard. Or use -mfpmath=sse to avoid the 80-bit registers entirely. Ian