Using The ARM Software Tools
============================


The ARM C Compiler (armcc)
--------------------------


About armcc
...........

The ARM C compiler is a mature, industrial-strength compiler, based on Codemist 
Ltd's multi-target, multi-language compiler suite (also known as the <Norcroft> 
C compiler).  

By default the ARM C compiler compiles ANSI C as defined by <American National 
Standard for Information Systems - Programming Language C>, X3J11/90-013, Feb 
14, 1990

The ARM C compiler also has a pcc mode, which accepts the dialect of C used by 
Berkeley Unix.  In this mode the compiler has been used to build a complete 
ARM-based Unix system (the RISCiX system).

For more background about the ARM C Compiler, and for recommended reading for C 
programmers, as well as full technical information on the ARM C Compiler see <"
The ARM C Compiler>" of the Reference Manual.


Invoking armcc
..............

The general form of the command for invoking the ARM C compiler is:

    armcc <options> <sourcefile>

By default, the C compiler looks for source files, and creates object, 
assembler and listing files, in the current directory.

Many aspects of the compiler's operation can be controlled via command-line 
options. All options are prefixed by a minus sign.

There are two classes of option: keywords and flags. Keywords are recognised in 
upper case or lower case. A flag is a single letter, the case of which is 
sometimes important to the ARM C compiler.

Because some systems (such as Unix) are very case sensitive, the case of flags 
is most important when you are building portable <makefiles>. By using the 
conventions common to many C compilers, you can move a makefile between 
different environments at minimum cost.


Keyword Options 
................


-help

Give a summary of the compiler's command line options.


-pcc

Compile (BSD 4.2) portable C compiler C. This dialect is based on the original 
Kernighan and Ritchie (K&R) definition of C, and is the one used on Unix 
systems. The -pcc keyword alters the language accepted by the compiler, but the 
built-in ANSI headers are still used. For more details on this, see section "
<PCC Compatibility Mode>" of the Reference Manual.


-fussy or -strict

Be extra strict about enforcing conformance to the ANSI standard or to pcc 
conventions (e.g. prohibit the <volatile> qualifier in -pcc mode).


-list

Create a listing file. This consists of lines of source interleaved with error 
and warning messages. Finer control over the contents of this file may be 
obtained using the -f flag (see"<Controlling Additional Compiler Features>" 
starting on page13).


-littleend or -li

Compile code for an ARM operating with little-endian (least significant byte 
has lowest address) memory.


-bigend or -bi

Compile code for an ARM operating with big-endian (most significant byte has 
lowest address) memory.

By default, the ARM C compiler compiles code with the same byte order as the 
host system. However, most releases of the ARM C compiler, for most hosts, 
allow this default to be configured when the compiler is installed, so it is 
not usually necessary to use either of these options (see "<The ARM Tool 
Reconfiguration Utility (reconfig)>" for more information).


-apcs [3]<qualifiers>

Specify which variant of the ARM Procedure Call Standard is to be used by the 
compiler.  The default is set up when <armcc> is configured, and for ease of 
use can be reconfigured using the <reconfig> tool - see "<The ARM Tool 
Reconfiguration Utility (reconfig)>" for details.  
Alternatively the default can be changed by use of this keyword option.

At least one qualifier must be present, and there must be no space between 
qualifiers.  The following qualifiers are permitted:

    /26[bit]                  26 bit APCS variant.
    /32[bit]                  32 bit APCS variant.
    /reent[rant]              Reentrant APCS variant.
    /nonreent[rant]           Non reentrant APCS variant.
    /swst[ackcheck]           Software stack checking APCS variant.
    /noswst[ackcheck]         No software stack checking APCS variant.
    /fpe2                     Floating point emulator 2 compatibility.
    /fpe3                     Floating point emulator 3 compatibility.
    /fpr[egargs]              F.P. arguments passed in FP. registers.
    /nofpr[egargs]            F.P. arguments are not passed in F.P. registers

For details of the various APCS variants see "<ARM Procedure Call Standard>" 
starting on page38 of the Technical Specifications.


Flag Options
............

The flag options are listed below. Some of these are followed by an argument. 
Whenever this is the case, the ARM C compiler allows white space to be inserted 
between the flag letter and the argument. However, this is not always true of 
other C compilers, so in the following subsections we only list the form that 
would be acceptable to a Unix C compiler. Similarly, we only use the case of 
the letter that would be accepted by a Unix C compiler.

The descriptions are divided into several subsections, so that flags 
controlling related aspects of the compiler's operation are grouped together.


Controlling the linker


-c

Do not perform the link step. This merely compiles the source program(s), 
leaving the object file(s) in the current directory (or as directed by the -o 
flag). This is different from the -C option described in"<Preprocessor Flags>" 
starting on page9.


Preprocessor Flags


-I<directory-name>

This adds the specified directory to the list of places which are searched for 
included files (after the in-memory or source file directory, according to the 
type of include file). The directories are searched in the order in which they 
are given by multiple -I options.  See <"Included Files>" of 
the Reference Manual for full details.


-j<directory-list>

directory-list is a comma separated list of search directories. This option 
adds the list of directories specified to the end of the search path (ie. after 
all directories specified by -I options), but otherwise in the same way as -I. 

However, it also has the side effect of stopping system include files being 
searched for in the in-memory filing system before all other searches.  Instead 
the in-memory filing system is searched for system include files only after all 
other searches have failed.

Note that the in-memory filing system can be specified in -I and -j options by 
<:mem>.

-j is an ARM-specific flag and is not portable to other C systems. There may be 
at most one -j option on a command line. See "<Included Files>" starting on 
page61 of the Reference Manual for full details.


-E

If this flag is specified, only the preprocessor phase of the compiler is 
executed. The output from the preprocessor is sent to the standard output 
stream. It can be redirected to a file using the stream redirection notations 
common to Unix and MS-DOS (e.g.

    armcc -E something.c > rawc

By default, comments are stripped from the output, (but see <-C flag>, below).


-C

When used in conjunction with -E above, -C retains comments in preprocessor 
output. It is different from the -c flag, which is used to suppress the link 
operation.


-M

If this flag is specified, only the preprocessor phase of the compiler is 
executed (as with armcc -E) but the only output produced is a list, on the 
standard output stream, of <makefile> dependency lines suitable for use by a 
<make> utility. This can be redirected to a file using standard Unix/MS-DOS 
notation. For example:

    armcc -M xxx.c >> Makefile.


-Dsymbol=value

Define <symbol> as a preprocessor macro, as if by a line <#define symbol value> 
at the head of the source file.


-Dsymbol

Define <symbol> as a preprocessor macro, as if by a line <#define symbol> at t
he head of the source file.


-Usymbol

Undefine <symbol>, as if by a line <#undef symbol> at the head of the source 
file.


Controlling Code Generation


-g<Letters>

This flag is used to specify that debugging tables for use by the ARM Source 
Level Debugger (<armsd>) should be generated. It is followed by an optional set 
of letters which specify the level of information required. If no letters are 
present then all the information possible is generated. However, the tables can 
occupy large amounts of memory so it is sometimes useful to limit what is 
included as follows.


-gf

Generate information on functions and top-level variables (those declared 
outside of functions) only.


-gl

Generate information describing each line in the source file(s).


-gv

Generate information describing all variables.

The last three modifiers may be specified in any combination, e.g. -gfv.


-o file

The argument to the -o flag gives the name of the file which will hold the 
final output of the compilation step. In conjunction with -c, it gives the name 
of the object file; in conjunction with -S, it gives the name of the assembly 
language file. Otherwise, it names the final output of the link step.


-Ospace

Perform optimisations to reduce image size at the expense of increased 
execution time.


-Otime

Perform optimisations to reduce execution time at the expense of a larger 
image.


-p and -px

The -p flag makes the compiler generate code to count the number of times each 
function is executed. If -px is given, the compiler also generates code to 
count how often each basic block within each function is executed. The -px 
option is specific to ARM C, though -p is widely used by other C systems to 
request profiling.

At the end of a program run, the counts can be printed to stderr by calling the 
ARM C library function <_mapstore()>, or to a named file of your choice by 
calling <_fmapstore("filename")>.

The printed results are lists of <lineno>, <count> pairs. The <lineno> value is 
the number of a line in your source code, and count is the number of times it 
was executed. Note that <lineno> is ambiguous: it may refer to a line in an 
included file, but this is rare and usually causes no confusion.

Provided that the program wasn't compiled with the -ff option, blocks of counts 
will be interspersed with function names. In the simplest case the output is 
reduced to a list of line pairs like:

    function-name
          lineno: count

where <count> is the number of times the function was executed.

If -px was used, the <lineno> values within each function relate to the start 
of each basic block. Sometimes, a statement (such as a <for> statement) may 
generate more than one basic block, so there can be two different counts for 
the same line.

Profiled programs run slowly. For example, when compiled -p, Dhrystone 1.1 runs 
at about 5/8 speed; when compiled -px it runs at only about 3/8 speed.

There is no direct way to relate these execution counts to the amount, or 
proportion, of execution time spent in each section of code. Nor is there yet 
any tool for annotating a source listing with profile counts. Future releases 
of ARM C may address these issues.


-S

If the -S flag is specified, no object code is generated but a listing of the 
equivalent assembly language is written to a file. By default, the file is call
ed <name.s> in the current directory (where <name.c> is the name of the source 
file stripped of any leading directory names). The default can be overridden 
using the -o flag (see above).


-via <file>

If this option is specified then <file> is opened and more <armcc> command line 
arguments are read in from it.  This is intended mainly for hostings (such as 
the PC) where command line length is severely limited.


Controlling Warning Messages


-W<Letters>

The -W option controls the suppression of warning messages. Usually the 
compiler is very free with its warnings, as these tend to indicate potential 
portability problems or other hazards. However, too many warning messages can 
be a nuisance in the early stages of porting a program written in old-style C, 
so warnings can disabled.


-W

If no modifier letters are given, then all warnings are suppressed. If one or 
more letters follow the flag, then only the warnings controlled by those 
letters are suppressed.


-Wa

Give no "Use of = in a condition context" warning. This is given when the 
compiler encounters a statement such as:

    if (a = b) {... 

where it is quite possible that the author really did intend

    if ((a = b) != 0) {...

and also plausible that the author intended

    if (a == b) {...

but missed a key stroke. In new code, the deliberate use of the needlessly 
dangerous <if (a = b) ...>, should be avoided. This warning is also suppressed 
in -pcc mode.


-Wd

Give no "Deprecated declaration foo() - give arg types" message, given when a 
declaration without argument types is encountered in ANSI mode (the warning is 
suppressed anyway in -pcc mode).

In ANSI C, declarations like this are deprecated and a future version of the C 
standard may ban them. They are already illegal in C++. However, it is 
sometimes useful to suppress this warning when porting old code.


-Wf

Give no "Inventing extern int foo()" message, which may be useful when 
compiling old-style C in ANSI mode. This warning is suppressed in -pcc mode.


-Wn

Give no "Implicit narrowing cast" warning. This warning is issued when the 
compiler detects the implicit narrowing of a long expression in an int or char 
context, or the implicit narrowing of a floating point expression in an integer 
or narrower floating point context. Such implicit narrowings are almost always 
a source of problems when moving code developed using a fully 32-bit system 
(such as ARM C) to a C system in which ints occupy 16 bits and longs 32 bits 
(as is common on the IBM PC, Apple Macintosh, etc.).


-Wv

Give no "Implicit return in non-void context" warning. This is most often 
caused by a return from a function which was assumed to return int (because no 
other type was specified) but is in fact being used as a void function. Because 
the practice is widespread in old-style C, the warning is suppressed in -pcc 
mode.


Controlling Additional Compiler Features


-zp<LetterDigit>

This flag can be used to emulate #pragma directives. The letter and digit which 
follow it are the same characters that would follow the '-' of a #pragma 
directive. See the section "<Pragma Directives>" of the 
Reference Manual for details.


-zr<Number>

This flag allows the size of (most) LDMs and (all) STMs to be controlled 
between the limits of 3 and 16 registers transferred.  This can be used to help 
control interrupt latency where this is critical.


-f<Letters>

The -f flag described in this section controls a variety of compiler features, 
including certain checks more rigorous than usual. Like the -W flag it is 
followed by a string of modifier letters. At least one letter is required, 
though several may be given at once, for example, -ffah.


-fa

Check for certain types of data flow anomalies. The compiler performs data flow 
analysis as part of code generation. The checks enabled by this option indicate 
when an automatic variable could have been used before it has been assigned a 
value. The check is pessimistic and will sometimes report an anomaly where 
there is none, especially in code like the following:

    int initialised = 0, value;
    ...
          if (initialised) { int v = value; ...
          ...
          value = ...;  initialised = 1;

Here, we know that <value> is read if, and only if, <initialised> has been set 
(but in general, the argument may be delicate). As this is a semantic 
deduction, not a data flow implication, -fa will report an anomaly.

In general, it is useful to check all code using -fa at some stage during its 
development.


-fc

Enable the "limited pcc" option, designed to support the use of pcc-style 
header files in an otherwise strict ANSI mode (e.g. when using libraries of 
functions implemented in old-style C from an application written in ANSI C). 
This allows characters after #else and #endif preprocessor directives (which 
are ignored).

The "limited pcc" option also supports system programming in ANSI mode by 
suppressing warnings about explicit casts of integers to function pointers, and 
permitting the dollar character in identifiers, (linker-generated symbols often 
contain "$$" and all external symbols containing "$$" are reserved to the 
linker).


-fe

Check that external names used within the file are still unique when reduced to 
six case-insensitive characters. Some (now very old) linkers support as few as 
six significant characters in external symbol names. This can cause problems 
with clashes if a system uses two names such as <getExpr1> and <getExpr2>, 
which are only unique in the eighth character. The check can only be made 
within a single compilation unit (source file) so cannot catch all such 
problems. ARM C allows external names of up to 256 characters, so this is 
strictly a portability aid.


-ff

Do not embed function names in the code area. The compiler does this to make 
the output produced by the stack backtrace run time support function and the 
<_mapstore()> function (see "<-p and -px>") more readable. 
Removing the names from the compiler itself makes the code slightly smaller 
(about 5%). In general it is not useful to specify -ff with -p.


-fh

Check that all external objects are declared before use and that all file 
scoped static objects are used. If external objects are only declared in 
included header files (never in-line in a C source file) then these checks 
directly support good modular programming practices.


-fi

In the listing file (see "<-list>") list the lines from any 
files included with directives of the form:

    #include "file"


-fj

As above, but for files included by lines of the form:

    #include <file>


-fk

Use K&R search rules for locating included files (the current place is defined 
by the original source file and is not stacked; see section "<The Search Path>" 
starting on page61 of the Reference Manual for details).


-fm

Report on preprocessor symbols defined but not used during the compilation.


-fp

Report on explicit casts of integers into pointers, e.g.

    char *cp = (char *) anInteger;

(Implicit casts are reported anyway, unless suppressed by the -Wc option).


-fu

By default, if -list is specified, the compiler lists the source text as seen 
by the compiler after preprocessing. If -fu is specified then the unexpanded 
source text, as written by the user, is listed. For example, consider the line:

    p = NULL;         /* assume NULL #defined to be (0) */

By default, this will be listed as p = (0); with -fu specified, as p = NULL;.


-fv

Report on all unused declarations, including those from standard headers.


-fw

Allow string literals to be writeable, as expected by some Unix code, by 
allocating them in the program's data area rather than the notionally read-only 
code area. Note that this also prevents the re-use by the compiler of a 
multiple, occurring string literal.

When writing high-quality production software, you are encouraged to use at 
least the -fah options in the later stages of program development (the extra 
diagnostics produced can be annoying in the earlier stages).

 

 

