How can I read register value to variable with one inline assembler command? I am using gcc on old freeBSD system (v2.1 i386).
I have such code:
static volatile unsigned long r_eax, r_ebx;
asm ("movl %%eax, %0\n" :"=r"(r_eax));
asm ("movl %%ebx, %0\n" :"=r"(r_ebx));
As result I get this:
mov %eax,%eax
mov %eax,0x1944b8
mov 0x1944b8,%eax
mov %ebx,%eax
mov %eax,0x1944bc
mov 0x1944bc,%eax
But i need just:
mov %eax,0x1944b8
mov %ebx,0x1944bc
How can I achieve this result?
The __asm keyword invokes the inline assembler and can appear wherever a C or C++ statement is legal. It cannot appear by itself. It must be followed by an assembly instruction, a group of instructions enclosed in braces, or, at the very least, an empty pair of braces.
int x, y = 5; asm("add %0, %1, %2" : "=r"(x) : "r"(y), "r"(5)); Each operand is described by an operand constraint string followed by an expression in parentheses. The “r” in the operand constraint string indicates that the operand must be located in a register. The “=” indicates that the operand is written.
In computer programming, an inline assembler is a feature of some compilers that allows low-level code written in assembly language to be embedded within a program, among code that otherwise has been compiled from a higher-level language such as C or Ada.
clobbers is a comma-separated list of register names enclosed in double quotes. If an asm instruction updates registers that are not listed in the input or output of the asm statement, the registers must be listed as clobbered registers. The following register names are valid : r0 to r31. General purpose registers.
This does it for me (as long as r_eax
/ r_ebx
are static)
asm ("movl %%eax, %0\n"
"movl %%ebx, %1\n"
: "=m"(r_eax), "=m"(r_ebx));
Beware that, unless you specify assembly language statements within the same asm()
bracket, the compiler might decide to do all sorts of "interesting optimizations" in-between, including modifications to these regs.
Notice you are using constraints instructing gcc to put the result into a register. So it can not directly put it into memory. Since you only want to store values from registers already there, you don't even need any instructions, just constraints, like so:
__asm__ __volatile__ ("" : "=a" (r_eax), "=b" (r_ebx));
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With