cgccinline-assembly

Purpose of '*&x' in inline assembly?


Looking at some x86_64 GCC inline assembly, I have come across the following construct:

int x;
__asm__( "<opcode> %0" : "=m" (*&x) );
                               ^^^

This seems to be some quirk to make the compiler do... something. But on the C level, it's a no-op, so I am wondering... what is this reference-dereference for, and isn't there a less quirky way to achieve the same?


Solution

  • As far as I know, it doesn't serve any functional purpose at all. It would be functionally equivalent, and more concise, to simply write "=m" (x).

    There could be a certain logic to writing "=m" (*&x) or "m" (*&x) as a stylistic choice. Often when using inline assembly with an m operand, you already have a pointer to the memory to be used, and so then you need to use "m" (*ptr). This can be a little counterintuitive, since after all it is the value of ptr that will get used within the asm code. So it's easy to get this wrong and write "m" (ptr) instead, which the compiler won't catch as there are no type constraints on asm operands. Thus the author might have decided to always prefer to write a memory operand in the form "m" (*expr), and so in code where we have the variable x instead of a pointer to it, following this rule would lead to writing "m" (*&x).

    (The compiler would refuse to compile "=m" (&x) because &x is not an lvalue, but if it were an input operand instead, "m" (&x) could result in the compiler materializing the address of x in stack memory, which is of course not what is wanted. Current versions of gcc will treat "m" (&x) as an error, but in older versions it was a non-fatal warning, so perhaps in even older versions it was silently accepted.)

    On the other hand, in the commit that introduced this code, there are other instances where the "m" (x) form is used. Perhaps the commit contains code written by multiple authors, or a single author who simply didn't follow their own conventions consistently.


    Regarding some of the explanations suggested in other comments and answers: