On 2017/8/15 4:39, Marcel Keller wrote:
Hi,
I've found that the attached code behaves differently when compiling
with or without -O in GCC 7.2.
$ gcc asm.cpp ; ./a.out
1
$ gcc -O asm.cpp ; ./a.out
0
Looking at the compiled program in the second case, GCC seems to omit
the inline assembly:
00000000004004e7 <f(long*)>:
4004e7: f3 c3 repz retq
My understanding is that the "memory" cobbler should tell GCC to assume
that the assembly changes the memory (which it does). Am I missing
something here?
Best regards,
Marcel
The parameter `z` of your function is an input-output parameter, but you
tell GCC that it is an input one. Thus GCC assumes it is unchanged and
the whole asm block can be elided safely.
You are also using a wrong constraint for the RDI register. The correct
one is "D".
To tell GCC that you are using a parameter with input-output semantics,
write the asm statement as follows:
```c
void f(long* z)
{
asm(
"addl $1,%0"
: "+m"(*z) /* a memory input-output constraint */
: /* no input constraint */
);
}
```
The "m" constraint requires an lvalue, so you dereference the pointer
then pass the result to it. Since %0 is now effectively a memory
reference there must not be parentheses in the asm code above.
--
Best regards,
LH_Mouse