Inline asm: inputs and outputs
billo 120000DT0E Visits (3450)
Imagine that, for whatever reason, you wanted to add 88 to a program variable “x” using inline asm. Knowing that Power is a load-store architecture, you might design your asm like this…..
asm ("lwz 5, %0 \n"
"addi 5, 5, 88 \n"
"stw 5, %0 \n"
: "r5" );
Here we load x into a register (r5), add 88 to it, and store it back to x. We have designated x as a memory operand in the output list, as we are modifying it. We also used a “+” to indicate that we are using its original value as well as modifying it. We are also clobbering r5, as we are using that register for our calculations.
However, this is an overly complex asm for what we want to do. Although Power is load/store, you can rely upon the compiler’s implementation of the operands to get data into registers and to store it back. The asm can thus be re-written as this:
asm ( "addi %0,%0, 88 \n"
This is improved in a number of ways:
Notice that we are no longer using an “m” (i.e. “memory”) operand, but are now using an “r” (for register) operand, and we are letting the compiler take care of loading it with x, and storing its value back into x. NOTE: in a subsequent blog I will discuss why it's sometimes better to use a "b" constraint -- and this is one of those times! Look at the following posting to see why:
The overall lesson here is that it is rarely necessary to use explicit loads and stores in inline asm. One exception to this would be when using the “load with reservation” and “store conditional” instructions (lwarx/stwcx). Other exceptions could be the use of load-multiple or load-with-update instructions. These will be dealt with in future blog entries.
A guide to inline assembly for C and C++
Till next time…. Bill