You copied the Doc URL to your clipboard.

Named register variables

The compiler enables you to access registers of an ARM architecture-based processor or coprocessor using named register variables.


register type var-name __asm(reg);



is the type of the named register variable.

Any type of the same size as the register being named can be used in the declaration of a named register variable. The type can be a structure, but bitfield layout is sensitive to endianness.


is the name of the named register variable.


is a character string denoting the name of a register on an ARM architecture-based processor, or for coprocessor registers, a string syntax that identifies the coprocessor and corresponds with how you intend to use the variable.

Registers available for use with named register variables on ARM architecture-based processors are shown in Table 26.

Table 26. Named registers available on ARM architecture-based processors
RegisterCharacter string for __asmProcessors
APSR"apsr"All processors
CPSR"cpsr"All processors
BASEPRI"basepri"Cortex-M3, Cortex-M4
BASEPRI_MAX"basepri_max"Cortex-M3, Cortex-M4
CONTROL"control"Cortex-M0, Cortex-M1, Cortex-M3, Cortex-M4
DSP"dsp"Cortex-M0, Cortex-M1, Cortex-M3, Cortex-M4
EAPSR"eapsr"Cortex-M0, Cortex-M1, Cortex-M3, Cortex-M4
EPSR"epsr"Cortex-M0, Cortex-M1, Cortex-M3, Cortex-M4
FAULTMASK"faultmask"Cortex-M3, Cortex-M4
IAPSR"iapsr"Cortex-M0, Cortex-M1, Cortex-M3, Cortex-M4
IEPSR"iepsr"Cortex-M0, Cortex-M1, Cortex-M3, Cortex-M4
IPSR"ipsr"Cortex-M0, Cortex-M1, Cortex-M3, Cortex-M4
MSP"msp"Cortex-M0, Cortex-M1, Cortex-M3, Cortex-M4
PRIMASK"primask"Cortex-M0, Cortex-M1, Cortex-M3, Cortex-M4
PSP"psp"Cortex-M0, Cortex-M1, Cortex-M3, Cortex-M4
PSR"psr"Cortex-M0, Cortex-M1, Cortex-M3, Cortex-M4
r0 to r12"r0" to "r12"All processors
r13 or sp"r13" or "sp"All processors
r14 or lr"r14" or "lr"All processors
r15 or pc"r15" or "pc"All processors


All processors, apart from Cortex-M series processors.
XPSR"xpsr"Cortex-M0, Cortex-M1, Cortex-M3, Cortex-M4

On targets with floating-point hardware, the registers of Table 27 are also available for use with named register variables.

Table 27. Named registers available on targets with floating-point hardware
RegisterCharacter string for __asm


Some registers are not available on some architectures.


You can declare named register variables as global variables. You can declare some, but not all, named register variables as local variables. In general, do not declare VFP registers and core registers as local variables. Do not declare caller-save registers, such as R0, as local variables.


In Example 12, apsr is declared as a named register variable for the "apsr" register:

register unsigned int apsr __asm("apsr");
apsr = ~(~apsr | 0x40);

This generates the following instruction sequence:

MRS r0,APSR ; formerly CPSR
BIC r0,r0,#0x40
MSR CPSR_c, r0

In Example 13, PMCR is declared as a register variable associated with coprocessor cp15, with CRn = c9, CRm = c12, opcode1 = 0, and opcode2 = 0, in an MCR or an MRC instruction:

register unsigned int PMCR __asm("cp15:0:c9:c12:0");

__inline void __reset_cycle_counter(void)
    PMCR = 4;

The disassembled output is as follows:

__reset_cycle_counter PROC
    MOV    r0,#4
    MCR    p15,#0x0,r0,c9,c12,#0
    BX     lr

In Example 14, cp15_control is declared as a register variable that is used to access a coprocessor register. This example enables the MMU using CP15:

register unsigned int cp15_control __asm("cp15:0:c1:c0:0");
cp15_control |= 0x1;

The following instruction sequence is generated:

MRC  p15,#0x0,r0,c1,c0,#0
ORR  r0,r0,#1
MCR  p15,#0x0,r0,c1,c0,#0

Example 15 for Cortex-M3 declares _msp, _control and _psp as named register variables to set up stack pointers:

register unsigned int _control __asm("control");
register unsigned int _msp     __asm("msp");
register unsigned int _psp     __asm("psp");void init(void)
  _msp = 0x30000000;        // set up Main Stack Pointer
  _control = _control | 3;  // switch to User Mode with Process Stack
  _psp = 0x40000000;        // setup Process Stack Pointer

This generates the following instruction sequence:

  MOV r0,#0x30000000
  MSR MSP,r0
  ORR r0,r0,#3
  MOV r0,#0x40000000
  MSR PSP,r0
  BX lr