7.6 --apcs=qualifier...qualifier

Controls interworking and position independence when generating code.

By specifying qualifiers to the --apcs command-line option, you can define the variant of the Procedure Call Standard for the ARM architecture (AAPCS) used by the compiler.

Syntax

--apcs=qualifier...qualifier
Where qualifier...qualifier denotes a list of qualifiers. There must be:
Each instance of qualifier must be one of:
/interwork
/nointerwork
Generates code with or without ARM/Thumb interworking support. The default is /nointerwork, except for ARMv5T and later where the default is /interwork.
/ropi
/noropi
Enables or disables the generation of Read-Only Position-Independent (ROPI) code. The default is /noropi.
/[no]pic is an alias for /[no]ropi.
/rwpi
/norwpi
Enables or disables the generation of Read/Write Position-Independent (RWPI) code. The default is /norwpi.
/[no]pid is an alias for /[no]rwpi.
/fpic
/nofpic
Enables or disables the generation of read-only position-independent code where relative address references are independent of the location where your program is loaded.
/hardfp
/softfp
Requests hardware or software floating-point linkage. This enables the procedure call standard to be specified separately from the version of the floating-point hardware available through the --fpu option. It is still possible to specify the procedure call standard by using the --fpu option, but ARM recommends that you use --apcs instead.

Note

The / prefix is optional for the first qualifier, but must be present to separate subsequent qualifiers in the same --apcs option. For example, --apcs=/nointerwork/noropi/norwpi is equivalent to --apcs=nointerwork/noropi/norwpi.
You can specify multiple qualifiers using either a single --apcs option or multiple --apcs options. For example, --apcs=/nointerwork/noropi/norwpi is equivalent to --apcs=/nointerwork --apcs=noropi/norwpi.

Default

If you do not specify an --apcs option, the compiler assumes --apcs=/nointerwork/noropi/norwpi/nofpic.

Usage

/interwork
/nointerwork
By default, code is generated:
  • Without interworking support, that is /nointerwork, unless you specify a --cpu option that corresponds to architecture ARMv5T or later.
  • With interworking support, that is /interwork, on ARMv5T and later. ARMv5T and later architectures provide direct support to interworking by using instructions such as BLX and load to program counter instructions.
/ropi
/noropi
If you select the /ropi qualifier to generate ROPI code, the compiler:
  • Addresses read-only code and data PC-relative.
  • Sets the Position Independent (PI) attribute on read-only output sections.

Note

--apcs=/ropi is not supported when compiling C++.
/rwpi
/norwpi
If you select the /rwpi qualifier to generate RWPI code, the compiler:
  • addresses writable data using offsets from the static base register sb. This means that:
    • The base address of the RW data region can be fixed at runtime.
    • Data can have multiple instances.
    • Data can be, but does not have to be, position-independent.
  • Sets the PI attribute on read/write output sections.

Note

Because the --lower_rwpi option is the default, code that is not RWPI is automatically transformed into equivalent code that is RWPI. This static initialization is done at runtime by the C++ constructor mechanism, even for C.
/fpic
/nofpic
If you select this option, the compiler:
  • Accesses all static data using PC-relative addressing.
  • Accesses all imported or exported read-write data using a Global Offset Table (GOT) entry created by the linker.
  • Accesses all read-only data relative to the PC.
You do not have to compile with /fpic if you are building either a static image or static library.
The use of /fpic is supported when compiling C++. In this case, virtual function tables and typeinfo are placed in read-write areas so that they can be accessed relative to the location of the PC.
/hardfp
If you use /hardfp, the compiler generates code for hardware floating-point linkage. Hardware floating-point linkage uses the FPU registers to pass the arguments and return values.
/hardfp interacts with or overrides explicit or implicit use of --fpu as follows:
The /hardfp and /softfp qualifiers are mutually exclusive.
  • If floating-point support is not permitted (for example, because --fpu=none is specified, or because of other means), /hardfp is ignored.
  • If floating-point support is permitted, but without floating-point hardware (--fpu=softvfp), /hardfp gives an error.
  • If floating-point hardware is available and the hardfp calling convention is used (--fpu=vfp...), /hardfp is ignored.
  • If floating-point hardware is present and the softfp calling convention is used (--fpu=softvfp+vfp...), /hardfp gives an error.
/softfp
If you use /softfp, software floating-point linkage is used. Software floating-point linkage means that the parameters and return value for a function are passed using the ARM integer registers r0 to r3 and the stack.
/softfp interacts with or overrides explicit or implicit use of --fpu as follows:
The /hardfp and /softfp qualifiers are mutually exclusive.
  • If floating-point support is not permitted (for example, because --fpu=none is specified, or because of other means), /softfp is ignored.
  • If floating-point support is permitted, but without floating-point hardware (--fpu=softvfp), /softfp is ignored because the state is already /softfp.
  • If floating-point hardware is present, /softfp forces the softfp (--fpu=softvfp+vfp...) calling convention.

Restrictions

There are restrictions when you compile code with /ropi, or /rwpi, or /fpic.
/ropi
The main restrictions when compiling with /ropi are:
  • The use of --apcs=/ropi is not supported when compiling C++. You can compile only the C subset of C++ with /ropi.
  • Some constructs that are legal C do not work when compiled for --apcs=/ropi. For example:
    extern const int ci; // ro
    const int *p2 = &ci; // this static initialization
                         // does not work with --apcs=/ropi
    
    To enable such static initializations to work, compile your code using the --lower_ropi option. For example:
    armcc --apcs=/ropi --lower_ropi
/rwpi
The main restrictions when compiling with /rwpi are:
  • Some constructs that are legal C do not work when compiled for --apcs=/rwpi. For example:
    int i;               // rw
    int *p1 = &i;        // this static initialization
                         // does not work with --apcs=/rwpi
                         // --no_lower_rwpi
    
    To enable such static initializations to work, compile your code using the --lower_rwpi option. For example:
    armcc --apcs=/rwpi
    

    Note

    You do not have to specify --lower_rwpi, because this is the default.
Related concepts
4.51 Compiler options for floating-point linkage and computations
4.42 Default selection of hardware or software floating-point support
Related reference
7.70 --fpu=name compiler option
7.107 --lower_ropi, --no_lower_ropi
7.108 --lower_rwpi, --no_lower_rwpi
Related information
Procedure Call Standard for the ARM Architecture
ARM C libraries and multithreading
Overview of veneers
Non-ConfidentialPDF file icon PDF versionARM DUI0375F
Copyright © 2007, 2008, 2011, 2012, 2014 ARM. All rights reserved.