This discussion has been locked.
You can no longer post new replies to this discussion. If you have a question you can start a new discussion

gcc vs realview inline asm

MDK-ARM RealView

I am converting some gcc based code and I am wondering how to convert the following C inline asm. The RealView compiler has slightly different syntax for inline, and the manual seems to spend more time telling you what you can't do than showing you what works.

//gcc inline
asm volatile (        \ 
   "mrs r3,cpsr;"        \ 
   "bic r3,r3,#0xC0;"    \ 
   "msr cpsr,r3"         \ 
   :                     \ 
   :                     \ 
   : "r3"                \ 
)


As far as I can tell (and I could be missing something) from the gcc docs, this bit above clears the irq,fiq bits in the cspr, the 'volatile' keeps it all from being optimized away, and I think the "r3" notation tells the compiler that r3 is going to be messed with so preserve it. I assume that cpsr here is the real physical register (it wouldn't work otherwise), but 'r3' may be some virtual version with no connection to the real r3. Any substitute code I come up with would have to do all of the above things.

Not surprising the gcc code does not compile under RealView. 'asm' needs to be '__asm' (for C), I think 'volatile' is not supported in this way, and the : "r3" syntax is totally rejected as well.

The manual states that the inline register references will almost always be virtual and have nothing to do with the physical registers, but it does seem to make an exception for psr (I assume this means cpsr,spsr), so the following inline does compile. The manual suggests that RealView will automatically preserve any used regs (but hopefully allow direct access to cspr). What's missing is the 'volatile'. Does RealView automatically preserve & protect inline asm code or do I have to take extra steps?

int r3;//this ones virtual
_asm (
   mrs r3,cpsr
   bic r3,r3,#0xC0
   msr cpsr,r3
)

Another simple option (less efficient?) seems to be using the intrinsic functions:

__enable_irq;
__enable_fiq;

Another possibility may be to use the named register variable feature which is supposed to access the real physical register:

register unsigned int mycspr __asm ("cspr");
unsigned int value;
value = mycspr & 0xFFFFFF3F;
mycspr = value;

Another possibility is to use an embedded asm function:

__asm void disable_intrs(void)
{
   mrs r3,cpsr
   bic r3,r3,#0xC0
   msr cpsr,r3
}
disable_intrs()

I have not checked these out yet, so let me know if there are any problems/comments with these methods or if there is a method I missed.

0