<article>
<title>cc65 Users Guide
-<author>Ullrich von Bassewitz, <htmlurl url="mailto:uz@cc65.org" name="uz@cc65.org">
-<date>2000-09-03, 2001-10-02, 2005-08-01
+<author><url url="mailto:uz@cc65.org" name="Ullrich von Bassewitz">,<newline>
+<url url="mailto:gregdk@users.sf.net" name="Greg King">
+<date>2017-05-20
<abstract>
cc65 is a C compiler for 6502 targets. It supports several 6502 based home
<!-- Begin the document -->
-
<sect>Overview<p>
cc65 was originally a C compiler for the Atari 8-bit machines written by
-O Optimize code
-Oi Optimize code, inline more code
-Or Enable register variables
- -Os Inline some known functions
+ -Os Inline some standard functions
-T Include source as comment
-V Print the compiler version number
- -W Suppress warnings
+ -W warning[,...] Suppress warnings
-d Debug mode
-g Add debug info to object file
-h Help (this text)
Long options:
--add-source Include source as comment
+ --all-cdecl Make functions default to __cdecl__
--bss-name seg Set the name of the BSS segment
--check-stack Generate stack overflow checks
--code-name seg Set the name of the CODE segment
--debug-opt name Debug optimization steps
--dep-target target Use this dependency target
--disable-opt name Disable an optimization step
+ --eagerly-inline-funcs Eagerly inline some known functions
--enable-opt name Enable an optimization step
- --forget-inc-paths Forget include search paths
--help Help (this text)
--include-dir dir Set an include directory search path
+ --inline-stdfuncs Inline some standard functions
--list-opt-steps List all optimizer steps and exit
+ --list-warnings List available warning types for -W
--local-strings Emit string literals immediately
--memory-model model Set the memory model
--register-space b Set space available for register variables
<descrip>
+ <tag><tt>--all-cdecl</tt></tag>
+
+ Tells the compiler that functions which aren't declared explicitly with
+ either the <tt/__cdecl__/ or <tt/__fastcall__/ calling conventions should
+ have the cdecl convention. (Normally, functions that aren't variadic are
+ fast-called.)
+
+
<label id="option-bss-name">
<tag><tt>--bss-name seg</tt></tag>
using <tt/-Oi/ (<tt/-Oi/ is the same as <tt/-O --codesize 200/).
- <label id="option-cpu">
+ <label id="option--cpu">
<tag><tt>--cpu CPU</tt></tag>
- A new, still experimental option. You may specify "6502" or "65C02" as the
- CPU. 6502 is the default, so this will not change anything. Specifying 65C02
- will use a few 65C02 instructions when generating code. Don't expect too
- much from this option: It is still new (and may have bugs), and the
- additional instructions for the 65C02 are not that overwhelming.
+ Set the CPU, the compiler generates code for. You may specify "6502" or
+ "65C02" as the CPU. The default depends on the selected target (see option
+ <tt/<ref id="option-t" name="-t">/). It is the 6502 CPU for most targets or
+ if no target has been set. Specifying 65C02 will use a few 65C02
+ instructions when generating code. Don't expect too much from this option:
+ In most cases the difference in size and speed is just 1-2%.
<label id="option-create-dep">
is defined to the value "1".
- <tag><tt>--forget-inc-paths</tt></tag>
-
- Forget the builtin include paths. This is most useful when building
- customized C or runtime libraries, in which case the standard header
- files should be ignored.
-
-
<tag><tt>-g, --debug-info</tt></tag>
This will cause the compiler to insert a <tt/.DEBUGINFO/ command into the
symbols in a special section in the object file.
+ <label id="option-eagerly-inline-funcs">
+ <tag><tt>--eagerly-inline-funcs</tt></tag>
+
+ Have the compiler eagerly inline these functions from the C library:
+ <itemize>
+ <item><tt/memcpy()/
+ <item><tt/memset()/
+ <item><tt/strcmp()/
+ <item><tt/strcpy()/
+ <item><tt/strlen()/
+ <item>most of the functions declared in <tt/<ctype.h>/
+ </itemize>
+
+ Note: This has two consequences:
+ <itemize>
+ <item>You may not use names of standard C functions for your own functions.
+ If you do that, your program is not standard-compliant anyway; but,
+ using <tt/--eagerly-inline-funcs/ actually will break things.
+ <p>
+ <item>The inlined string and memory functions will not handle strings or
+ memory areas larger than 255 bytes. Similarly, the inlined <tt/is..()/
+ functions will not work with values outside the char. range (such as
+ <tt/EOF/).
+ <p>
+ </itemize>
+
+ <tt/--eagerly-inline-funcs/ implies the <tt><ref id="option-inline-stdfuncs"
+ name="--inline-stdfuncs"></tt> command line option.
+
+ See also <tt><ref id="pragma-allow-eager-inline" name="#pragma allow-eager-inline"></tt>.
+
+
<tag><tt>-h, --help</tt></tag>
Print the short option summary shown above.
+ <label id="option-inline-stdfuncs">
+ <tag><tt>--inline-stdfuncs</tt></tag>
+
+ Allow the compiler to inline some standard functions from the C library like
+ strlen. This will not only remove the overhead for a function call, but will
+ make the code visible for the optimizer. See also the <tt><ref id="option-O"
+ name="-Os"></tt> command line option and <tt><ref id="pragma-inline-stdfuncs"
+ name="#pragma inline-stdfuncs"></tt>.
+
+
+ <label id="option-list-warnings">
+ <tag><tt>--list-warnings</tt></tag>
+
+ List the names of warning types available for use with <tt><ref
+ id="option-W" name="-W"></tt>.
+
+
<label id="option-local-strings">
<tag><tt>--local-strings</tt></tag>
- Emit string literals to the data segment when they're encountered in the
- source. The default is to keep string literals until end of assembly, merge
- read only literals if possible, and then output the literals into the data
- or rodata segment that is active at that point. Use of this option prevents
- merging of duplicate strings, but the options that change the name of one of
- the data segments will work.
+ Emit string literals into the rodata segment as soon as they're encountered
+ in the source (even if you do nothing but get the sizeof those strings). The
+ default is to keep string literals until end of assembly, merge read only
+ literals if possible, and then output the literals into the data or rodata
+ segment that is active at that point. Use of this option prevents merging of
+ duplicate strings, but the options that change the name of one of the data
+ segments will work.
You can also use <tt><ref id="pragma-local-strings"
name="#pragma local-strings"></tt> for fine grained control.
will. c99 mode is actually c89 mode with a few selected C99 extensions.
- <label id="option-standard">
+ <label id="option-t">
<tag><tt>-t target, --target target</tt></tag>
- This option is used to set the target system. The target system
- determines things like the character set that is used for strings and
- character constants. The following target systems are supported:
+ This option is used to set the target system. The target system determines
+ the character set that is used for strings and character constants and the
+ default CPU. The CPU setting can be overriden by use of the <tt/<ref
+ id="option--cpu" name="--cpu">/ option.
+
+ The following target systems are supported:
<itemize>
<item>none
<item>apple2
<item>apple2enh
<item>atari
+ <item>atarixl
<item>atmos
<item>c16 (works also for the c116 with memory up to 32K)
<item>c64
<item>c128
<item>cbm510 (CBM-II series with 40 column video)
<item>cbm610 (all CBM-II II computers with 80 column video)
- <item>geos
+ <item>geos-apple
+ <item>geos-cbm
<item>lunix
<item>lynx
<item>nes
+ <item>osic1p
<item>pet (all CBM PET systems except the 2001)
<item>plus4
+ <item>sim6502
+ <item>sim65c02
<item>supervision
+ <item>telestrat
<item>vic20
</itemize>
using
<tscreen><verb>
- void f (void)
- {
- unsigned a = 1;
- ...
- }
+ void f (void)
+ {
+ unsigned a = 1;
+ ...
+ }
</verb></tscreen>
the variable <tt/a/ will always have the value <tt/1/ when entering the
function and using <tt/-Cl/, while in
<tscreen><verb>
- void f (void)
- {
- static unsigned a = 1;
- ....
- }
+ void f (void)
+ {
+ static unsigned a = 1;
+ ....
+ }
</verb></tscreen>
the variable <tt/a/ will have the value <tt/1/ only the first time that the
name="--register-vars">/ command line option, and the <ref
id="register-vars" name="discussion of register variables"> below.
- Using <tt/-Os/ will force the compiler to inline some known functions from
- the C library like strlen. Note: This has two consequences:
- <p>
- <itemize>
- <item>You may not use names of standard C functions in your own code. If you
- do that, your program is not standard compliant anyway, but using
- <tt/-Os/ will actually break things.
- <p>
- <item>The inlined string and memory functions will not handle strings or
- memory areas larger than 255 bytes. Similarly, the inlined <tt/is..()/
- functions will not work with values outside the char. range (such as
- <tt/EOF/).
- <p>
- </itemize>
- <p>
+ Using <tt/-Os/ will allow the compiler to inline some standard functions
+ from the C library like strlen. This will not only remove the overhead
+ for a function call, but will make the code visible for the optimizer.
+ See also the <tt/<ref id="option-inline-stdfuncs" name="--inline-stdfuncs">/
+ command line option.
+
It is possible to concatenate the modifiers for <tt/-O/. For example, to
- enable register variables and inlining of known functions, you may use
+ enable register variables and inlining of standard functions, you may use
<tt/-Ors/.
<label id="option-W">
- <tag><tt>-W name[,name]</tt></tag>
+ <tag><tt>-W name[,name,...]</tt></tag>
This option allows to control warnings generated by the compiler. It is
- followed by a comma separated list of warnings that should be enabled or
+ followed by a comma-separated list of warnings that should be enabled or
disabled. To disable a warning, its name is prefixed by a minus sign. If
no such prefix exists, or the name is prefixed by a plus sign, the warning
is enabled.
- The following warning names are currently recognized:
+ The following warning names currently are recognized:
<descrip>
+ <tag><tt/const-comparison/</tag>
+ Warn if the result of a comparison is constant.
<tag><tt/error/</tag>
Treat all warnings as errors.
+ <tag><tt/no-effect/</tag>
+ Warn about statements that don't have an effect.
+ <tag><tt/remap-zero/</tag>
+ Warn about a <tt/<ref id="pragma-charmap" name="#pragma charmap()">/
+ that changes a character's code number from/to 0x00.
+ <tag><tt/struct-param/</tag>
+ Warn when passing structs by value.
<tag><tt/unknown-pragma/</tag>
- Warn about known #pragmas.
+ Warn about #pragmas that aren't recognized by cc65.
<tag><tt/unused-label/</tag>
Warn about unused labels.
<tag><tt/unused-param/</tag>
Warn about unused variables.
</descrip>
- You may also use <tt><ref id="pragma-warn" name="#pragma warn"></tt> to
- control this setting for smaller pieces of code from within your code.
+ The full list of available warning names can be retrieved by using the
+ option <tt><ref id="option-list-warnings" name="--list-warnings"></tt>.
+
+ You may use also <tt><ref id="pragma-warn" name="#pragma warn"></tt> to
+ control this setting, for smaller pieces of code, from within your sources.
</descrip><p>
+
<sect>Input and output<p>
The compiler will accept one C file per invocation and create a file with
the same base name, but with the extension replaced by ".s". The output
-file contains assembler code suitable for the use with the ca65 macro
+file contains assembler code suitable for use with the ca65 macro
assembler.
-Include files in single quotes are searched in the following places:
+Include files in quotes are searched in the following places:
<enum>
-<item>The current directory.
-<item>The value of the environment variable <tt/CC65_INC/ if it is defined.
+<item>The current file's directory.
<item>Any directory added with the <tt/-I/ option on the command line.
+<item>The value of the environment variable <tt/CC65_INC/ if it is defined.
</enum>
Include files in angle brackets are searched in the following places:
<enum>
-<item>A compiled in directory which is often <tt>/usr/lib/cc65/include</tt> on
- Linux systems.
+<item>Any directory added with the <tt/-I/ option on the command line.
<item>The value of the environment variable <tt/CC65_INC/ if it is defined.
<item>A subdirectory named <tt/include/ of the directory defined in the
environment variable <tt/CC65_HOME/, if it is defined.
-<item>Any directory added with the <tt/-I/ option on the command line.
+<item>An optionally compiled-in directory.
</enum>
<itemize>
-<item> The datatypes "float" and "double" are not available.
- <p>
-<item> C Functions may not return structs (or unions), and structs may not
+<item> The datatypes "float" and "double" are not available.
+ <p>
+<item> C Functions may not return structs (or unions), and structs may not
be passed as parameters by value. However, struct assignment *is*
- possible.
- <p>
-<item> Part of the C library is available only with fastcall calling
- conventions (see below). It means that you must not mix pointers to
- those functions with pointers to user-written, not-fastcall functions.
- <p>
-<item> The <tt/volatile/ keyword doesn't have an effect. This is not as bad
+ possible.
+ <p>
+<item> Most of the C library is available with only the fastcall calling
+ convention (<ref id="extension-fastcall" name="see below">). It means
+ that you must not mix pointers to those functions with pointers to
+ user-written, cdecl functions (the calling conventions are incompatible).
+ <p>
+<item> The <tt/volatile/ keyword has almost no effect. That is not as bad
as it sounds, since the 6502 has so few registers that it isn't
possible to keep values in registers anyway.
- <p>
+ <p>
</itemize>
There may be some more minor differences I'm currently not aware of. The
<itemize>
-<item> The compiler allows to insert assembler statements into the output
- file. The syntax is
-
- <tscreen><verb>
- asm (<string literal>[, optional parameters]) ;
- </verb></tscreen>
- or
- <tscreen><verb>
- __asm__ (<string literal>[, optional parameters]) ;
- </verb></tscreen>
-
- The first form is in the user namespace and is disabled if the <tt/-A/
- switch is given.
-
- There is a whole section covering inline assembler statements,
- <ref id="inline-asm" name="see there">.
- <p>
-
-<item> There is a special calling convention named "fastcall".
- The syntax for a function declaration using fastcall is
-
- <tscreen><verb>
- <return type> fastcall <function name> (<parameter list>)
- </verb></tscreen>
- or
- <tscreen><verb>
- <return type> __fastcall__ <function name> (<parameter list>)
- </verb></tscreen>
- An example would be
- <tscreen><verb>
- void __fastcall__ f (unsigned char c)
- </verb></tscreen>
- The first form of the fastcall keyword is in the user namespace and can
- therefore be disabled with the <tt><ref id="option--standard"
+<item> The compiler allows to insert assembler statements into the output
+ file. The syntax is
+
+ <tscreen><verb>
+ asm [optional volatile] (<string literal>[, optional parameters]) ;
+ </verb></tscreen>
+ or
+ <tscreen><verb>
+ __asm__ [optional volatile] (<string literal>[, optional parameters]) ;
+ </verb></tscreen>
+
+ The first form is in the user namespace; and, is disabled if the <tt/-A/
+ switch is given.
+
+ There is a whole section covering inline assembler statements,
+ <ref id="inline-asm" name="see there">.
+ <p>
+
+<label id="extension-fastcall">
+<item> The normal calling convention -- for non-variadic functions -- is
+ named "fastcall". The syntax for a function declaration that
+ <em/explicitly/ uses fastcall is
+
+ <tscreen><verb>
+ <return type> fastcall <function name> (<parameter list>)
+ </verb></tscreen>
+ or
+ <tscreen><verb>
+ <return type> __fastcall__ <function name> (<parameter list>)
+ </verb></tscreen>
+ An example is
+ <tscreen><verb>
+ void __fastcall__ f (unsigned char c)
+ </verb></tscreen>
+ The first form of the fastcall keyword is in the user namespace and can
+ therefore be disabled with the <tt><ref id="option--standard"
name="--standard"></tt> command line option.
- For functions declared as <tt/fastcall/, the rightmost parameter is not
- pushed on the stack but left in the primary register when the function
- is called. This will reduce the cost when calling assembler functions
- significantly, especially when the function itself is rather small.
- <p>
-
-<item> There are two pseudo variables named <tt/__AX__/ and <tt/__EAX__/.
- Both refer to the primary register that is used by the compiler to
- evaluate expressions or return function results. <tt/__AX__/ is of
- type <tt/unsigned int/ and <tt/__EAX__/ of type <tt/long unsigned int/
- respectively. The pseudo variables may be used as lvalue and rvalue as
- every other variable. They are most useful together with short
- sequences of assembler code. For example, the macro
-
- <tscreen><verb>
- #define hi(x) \
+ For functions that are <tt/fastcall/, the rightmost parameter is not
+ pushed on the stack but left in the primary register when the function
+ is called. That significantly reduces the cost of calling those functions.
+ <p>
+
+<item> There is another calling convention named "cdecl". Variadic functions
+ (their prototypes have an ellipsis [<tt/.../]) always use that
+ convention. The syntax for a function declaration using cdecl is
+
+ <tscreen><verb>
+ <return type> cdecl <function name> (<parameter list>)
+ </verb></tscreen>
+ or
+ <tscreen><verb>
+ <return type> __cdecl__ <function name> (<parameter list>)
+ </verb></tscreen>
+ An example is
+ <tscreen><verb>
+ int* __cdecl__ f (unsigned char c)
+ </verb></tscreen>
+
+ The first form of the cdecl keyword is in the user namespace;
+ and therefore, can be disabled with the <tt/<ref id="option--standard"
+ name="--standard">/ command-line option.
+
+ For functions that are <tt/cdecl/, the rightmost parameter is pushed
+ onto the stack before the function is called. That increases the cost
+ of calling those functions, especially when they are called from many
+ places.
+ <p>
+
+<item> There are two pseudo variables named <tt/__AX__/ and <tt/__EAX__/.
+ Both refer to the primary register that is used by the compiler to
+ evaluate expressions or return function results. <tt/__AX__/ is of
+ type <tt/unsigned int/ and <tt/__EAX__/ of type <tt/long unsigned int/
+ respectively. The pseudo variables may be used as lvalue and rvalue as
+ every other variable. They are most useful together with short
+ sequences of assembler code. For example, the macro
+
+ <tscreen><verb>
+ #define hi(x) \
(__AX__ = (x), \
asm ("txa"), \
asm ("ldx #$00"), \
__AX__)
- </verb></tscreen>
+ </verb></tscreen>
- will give the high byte of any unsigned value.
- <p>
+ will give the high byte of any unsigned value.
+ <p>
+
+<item> Inside a function, the identifier <tt/__func__/ gives the name of the
+ current function as a string. Outside of functions, <tt/__func__/ is
+ undefined.
+ Example:
-<item> Inside a function, the identifier <tt/__func__/ gives the name of the
- current function as a string. Outside of functions, <tt/__func__/ is
- undefined.
- Example:
+ <tscreen><verb>
+ #define PRINT_DEBUG(s) printf ("%s: %s\n", __func__, s);
+ </verb></tscreen>
- <tscreen><verb>
- #define PRINT_DEBUG(s) printf ("%s: %s\n", __func__, s);
- </verb></tscreen>
+ The macro will print the name of the current function plus a given
+ string.
+ <p>
- The macro will print the name of the current function plus a given
- string.
- <p>
+<item> cc65 allows the initialization of <tt/void/ variables. This may be
+ used to create arbitrary structures that are more compatible with
+ interfaces written for assembler languages. Here is an example:
-<item> cc65 allows the initialization of <tt/void/ variables. This may be
- used to create variable structures that are more compatible with
- interfaces written for assembler languages. Here is an example:
+ <tscreen><verb>
+ void GCmd = { (char)3, (unsigned)0x2000, (unsigned)0x3000 };
+ </verb></tscreen>
- <tscreen><verb>
- void GCmd = { (char)3, (unsigned)0x2000, (unsigned)0x3000 };
- </verb></tscreen>
+ That will be translated as follows:
- This will be translated as follows:
+ <tscreen><verb>
+ _GCmd:
+ .byte 3
+ .word $2000
+ .word $3000
+ </verb></tscreen>
- <tscreen><verb>
- _GCmd:
- .byte 3
- .word $2000
- .word $3000
- </verb></tscreen>
+ Since the variable is of type <tt/void/, you may not use it as-is.
+ However, taking the address of the variable results in a <tt/void*/
+ which may be passed to any function expecting a pointer. Also, the
+ <tt/sizeof/ operator will give the length of the initializer:
- Since the variable is of type <tt/void/ you may not use it as is.
- However, taking the address of the variable results in a <tt/void*/
- which may be passed to any function expecting a pointer.
+ <tscreen><verb>
+ GLen = sizeof GCmd;
+ </verb></tscreen>
- See the <url url="geos.html" name="GEOS library document"> for examples
- on how to use this feature.
- <p>
+ will assign the value 5 to <tt/GLen/.
+
+ See the <url url="geos.html" name="GEOS library document"> for examples
+ on how to use that feature.
+ <p>
<item> cc65 implements flexible array struct members as defined in the C99 ISO
standard. As an extension, these fields may be initialized. There are
<p>
+
<sect>Predefined macros<p>
The compiler defines several macros at startup:
<descrip>
<tag><tt>__APPLE2__</tt></tag>
- This macro is defined if the target is the Apple ][ (-t apple2).
+ This macro is defined if the target is the Apple ][ (-t apple2) or the enhanced Apple //e (-t apple2enh).
<tag><tt>__APPLE2ENH__</tt></tag>
This macro is defined if the target is the enhanced Apple //e (-t apple2enh).
+ <tag><tt>__ATARI2600__</tt></tag>
+
+ This macro is defined if the target is the Atari 2600 game console.
+
+ <tag><tt>__ATARI5200__</tt></tag>
+
+ This macro is defined if the target is the Atari 5200 game console.
+
<tag><tt>__ATARI__</tt></tag>
- This macro is defined if the target is one of the Atari computers
- (400/800/130XL/800XL).
+ This macro is defined if the target is the Atari 400/800 (-t atari) or the Atari 800XL/130XE (-t atarixl).
+
+ <tag><tt>__ATARIXL__</tt></tag>
+
+ This macro is defined if the target is the Atari 800XL/130XE (-t atarixl).
<tag><tt>__ATMOS__</tt></tag>
<tag><tt>__C128__</tt></tag>
- This macro is defined if the target is the c128 (-t c128).
+ This macro is defined if the target is the Commodore 128 (-t c128).
<tag><tt>__C16__</tt></tag>
- This macro is defined if the target is the c16 (-t c16).
+ This macro is defined if the target is the Commodore 16/116 (-t c16) or the Commodore Plus/4 (-t plus4).
<tag><tt>__C64__</tt></tag>
- This macro is defined if the target is the c64 (-t c64).
+ This macro is defined if the target is the Commodore 64 (-t c64).
<tag><tt>__CBM__</tt></tag>
<tag><tt>__CC65__</tt></tag>
This macro is always defined. Its value is the version number of the
- compiler in hex. For example, version 2.10.1 of the compiler has this macro
- defined as <tt/0x02A1/.
+ compiler in hex. For example, version 2.14 of the compiler has this macro
+ defined as <tt/0x02E0/.
<tag><tt>__CC65_STD__</tt></tag>
This macro expands to the date of translation of the preprocessing
translation unit in the form "Mmm dd yyyy".
+ <tag><tt>__EAGERLY_INLINE_FUNCS__</tt></tag>
+
+ Is defined if the compiler was called with the <tt><ref id="option-eagerly-inline-funcs"
+ name="--eagerly-inline-funcs"></tt> command line option.
+
<tag><tt>__FILE__</tt></tag>
This macro expands to a string containing the name of the C source file.
<tag><tt>__GEOS__</tt></tag>
- This macro is defined if you are compiling for the GEOS system (-t geos).
+ This macro is defined if you are compiling for one of the GEOS systems.
+
+ <tag><tt>__GEOS_APPLE__</tt></tag>
+
+ This macro is defined if you are compiling for the Apple GEOS system (-t geos-apple).
+
+ <tag><tt>__GEOS_CBM__</tt></tag>
+
+ This macro is defined if you are compiling for the GEOS 64/128 system (-t geos-cbm).
<tag><tt>__LINE__</tt></tag>
<tag><tt>__NES__</tt></tag>
- This macro is defined if the target is the NES (-t nes).
+ This macro is defined if the target is the Nintendo Entertainment System (-t nes).
<tag><tt>__OPT__</tt></tag>
Is defined if the compiler was called with the <tt/-Os/ command line option.
+ <tag><tt>__OSIC1P__</tt></tag>
+
+ This macro is defined if the target is the Ohio Scientific Challenger 1P
+ (-t osic1p).
+
<tag><tt>__PET__</tt></tag>
This macro is defined if the target is the PET family of computers (-t pet).
<tag><tt>__PLUS4__</tt></tag>
- This macro is defined if the target is the plus/4 (-t plus4).
+ This macro is defined if the target is the Commodore Plus/4 (-t plus4).
<tag><tt>__STDC_HOSTED__</tt></tag>
This macro is expands to the integer constant 1.
+ <tag><tt>__SIM6502__</tt></tag>
+
+ This macro is defined if the target is sim65 in 6502 mode (-t sim6502).
+
+ <tag><tt>__SIM65C02__</tt></tag>
+ This macro is defined if the target is sim65 in 65C02 mode (-t sim65c02).
+
<tag><tt>__SUPERVISION__</tt></tag>
- This macro is defined if the target is the supervision (-t supervision).
+ This macro is defined if the target is the Supervision (-t supervision).
+ <tag><tt>__TELESTRAT__</tt></tag>
+
+ This macro is defined if the target is the Telestrat (-t telestrat).
+
<tag><tt>__TIME__</tt></tag>
This macro expands to the time of translation of the preprocessing
<tag><tt>__VIC20__</tt></tag>
- This macro is defined if the target is the vic20 (-t vic20).
+ This macro is defined if the target is the Commodore VIC20 (-t vic20).
</descrip>
+
<sect>#pragmas<label id="pragmas"><p>
The compiler understands some pragmas that may be used to change code
before changing it. The value may later be restored by using the <tt/pop/
parameter with the <tt/#pragma/.
+
+<sect1><tt>#pragma allow-eager-inline ([push,] on|off)</tt><label id="pragma-allow-eager-inline"><p>
+
+ Allow eager inlining of known functions. If the argument is "off", eager
+ inlining is disabled, otherwise it is enabled. Please note that (in contrast
+ to the <tt><ref id="option-eagerly-inline-funcs" name="--eagerly-inline-funcs"></tt>
+ command line option) this pragma does not imply the <tt><ref id="option-inline-stdfuncs"
+ name="--inline-stdfuncs"></tt> command line option. Rather it marks code to be safe for
+ eager inlining of known functions if inlining of standard functions is enabled.
+
+ The <tt/#pragma/ understands the push and pop parameters as explained above.
+
+
<sect1><tt>#pragma bss-name ([push,] <name>)</tt><label id="pragma-bss-name"><p>
This pragma changes the name used for the BSS segment (the BSS segment
Example:
<tscreen><verb>
- #pragma bss-name ("MyBSS")
+ #pragma bss-name ("MyBSS")
</verb></tscreen>
<sect1><tt>#pragma charmap (<index>, <code>)</tt><label id="pragma-charmap"><p>
Each literal string and each literal character in the source is translated
- by use of a translation table. This translation table is preset when the
- compiler is started depending on the target system, for example to map
- ISO-8859-1 characters into PETSCII if the target is a commodore machine.
+ by use of a translation table. That translation table is preset when the
+ compiler is started, depending on the target system; for example, to map
+ ISO-8859-1 characters into PETSCII if the target is a Commodore machine.
This pragma allows to change entries in the translation table, so the
translation for individual characters, or even the complete table may be
- adjusted.
-
- Both arguments are assumed to be unsigned characters with a valid range of
- 1-255.
+ adjusted. Both arguments are assumed to be unsigned characters with a valid
+ range of 0-255.
- Beware of two pitfalls:
-
- <itemize>
- <item>The character index is actually the code of the character in the
- C source, so character mappings do always depend on the source
- character set. This means that <tt/#pragma charmap/ is not
- portable -- it depends on the build environment.
- <item>While it is possible to use character literals as indices, the
- result may be somewhat unexpected, since character literals are
- itself translated. For this reason I would suggest to avoid
- character literals and use numeric character codes instead.
- </itemize>
+ Beware of some pitfalls:
+ <itemize>
+ <item>The character index is actually the code of the character in the
+ C source; so, character mappings do always depend on the source
+ character set. That means that <tt/#pragma charmap()/ is not
+ portable -- it depends on the build environment.
+ <item>While it is possible to use character literals as indices, the
+ result may be somewhat unexpected, since character literals are
+ themselves translated. For that reason, I would suggest to avoid
+ character literals, and use numeric character codes instead.
+ <item>It is risky to change index <tt/0x00/, because string functions depend
+ on it. If it is changed, then the <tt/'\0'/ at the end of string
+ literals will become non-zero. Functions that are used on those
+ literals won't stop at the end of them. cc65 will warn you if you do
+ change that code number. You can turn off that <tt/remap-zero/ warning
+ if you are certain that you know what you are doing (see <tt/<ref
+ id="pragma-warn" name="#pragma warn()">/).
+ </itemize>
Example:
<tscreen><verb>
- /* Use a space wherever an 'a' occurs in ISO-8859-1 source */
- #pragma charmap (0x61, 0x20);
+ /* Use a space wherever an 'a' occurs in ISO-8859-1 source */
+ #pragma charmap (0x61, 0x20);
</verb></tscreen>
The <tt/#pragma/ understands the push and pop parameters as explained above.
+
<sect1><tt>#pragma code-name ([push,] <name>)</tt><label id="pragma-code-name"><p>
This pragma changes the name used for the CODE segment (the CODE segment
Example:
<tscreen><verb>
- #pragma code-name ("MyCODE")
+ #pragma code-name ("MyCODE")
</verb></tscreen>
Example:
<tscreen><verb>
- #pragma data-name ("MyDATA")
+ #pragma data-name ("MyDATA")
</verb></tscreen>
+<sect1><tt>#pragma inline-stdfuncs ([push,] on|off)</tt><label id="pragma-inline-stdfuncs"><p>
+
+ Allow the compiler to inline some standard functions from the C library like
+ strlen. If the argument is "off", inlining is disabled, otherwise it is enabled.
+
+ See also the <tt/<ref id="option-inline-stdfuncs" name="--inline-stdfuncs">/
+ command line option.
+
+ The <tt/#pragma/ understands the push and pop parameters as explained above.
+
+
<sect1><tt>#pragma local-strings ([push,] on|off)</tt><label id="pragma-local-strings"><p>
When "on", emit string literals to the data segment when they're encountered
remembered and output as a whole when translation is finished.
+<sect1><tt>#pragma message (<message>)</tt><label id="pragma-message"><p>
+
+ This pragma is used to display informational messages at compile-time.
+
+ The message intented to be displayed must be a string literal.
+
+ Example:
+ <tscreen><verb>
+ #pragma message ("in a bottle")
+ </verb></tscreen>
+
+ Results in the compiler outputting the following to stderr:
+ <tscreen><verb>
+ example.c(42): Note: in a bottle
+ </verb></tscreen>
+
+
<sect1><tt>#pragma optimize ([push,] on|off)</tt><label id="pragma-optimize"><p>
Switch optimization on or off. If the argument is "off", optimization is
Example:
<tscreen><verb>
- #pragma rodata-name ("MyRODATA")
+ #pragma rodata-name ("MyRODATA")
</verb></tscreen>
Example:
<tscreen><verb>
- #pragma regvaraddr(on) /* Allow taking the address
- * of register variables
- */
+ #pragma regvaraddr(on) /* Allow taking the address
+ * of register variables
+ */
</verb></tscreen>
Switch compiler warnings on or off. "name" is the name of a warning (see the
<tt/<ref name="-W" id="option-W">/ compiler option for a list). The name is
- either followed by "pop", which restores the last pushed state, or by "on" or
+ followed either by "pop", which restores the last pushed state, or by "on" or
"off", optionally preceeded by "push" to push the current state before
changing it.
Example:
<tscreen><verb>
/* Don't warn about the unused parameter in function func */
- #pragma warn (unused-param, push, off)
+ #pragma warn (unused-param, push, off)
static int func (int unused)
{
return 0;
#pragma warn (unused-param, pop)
</verb></tscreen>
+
+<sect1><tt>#pragma wrapped-call (push, <name>, <identifier>)</tt><label id="pragma-wrapped-call"><p>
+
+ This pragma sets a wrapper for functions, often used for trampolines.
+
+ The name is a function returning <tt/void/, and taking no parameters.
+ It must preserve the CPU's <tt/A/ and <tt/X/ registers if it wraps any
+ <tt/__fastcall__/ functions that have parameters. It must preserve
+ the <tt/Y/ register if it wraps any variadic functions (they have "<tt/.../"
+ in their prototypes).
+
+ The identifier is an 8-bit number that's set into <tt/tmp4/.
+
+ The address of a wrapped function is passed in <tt/ptr4/. The wrapper can
+ call that function by using "<tt/jsr callptr4/".
+
+ This feature is useful, for example, with banked memory, to switch banks
+ automatically to where a wrapped function resides, and then to restore the
+ previous bank when it returns.
+
+ The <tt/#pragma/ requires the push or pop argument as explained above.
+
+ Example:
+ <tscreen><verb>
+/* Note that this code can be in a header. */
+void mytrampoline(void); /* Doesn't corrupt __AX__ */
+
+#pragma wrapped-call (push, mytrampoline, 5)
+void somefunc1(void);
+void somefunc2(int, char *);
+#pragma wrapped-call (pop)
+ </verb></tscreen>
+
+
<sect1><tt>#pragma writable-strings ([push,] on|off)</tt><label id="pragma-writable-strings"><p>
Changes the storage location of string literals. For historical reasons,
Example:
<tscreen><verb>
- extern int foo;
- #pragma zpsym ("foo"); /* foo is in the zeropage */
+ extern int foo;
+ #pragma zpsym ("foo"); /* foo is in the zeropage */
</verb></tscreen>
-
<sect>Register variables<label id="register-vars"><p>
The runtime for all supported platforms has 6 bytes of zero page space
syntax is
<tscreen><verb>
- asm (<string literal>[, optional parameters]) ;
+ asm [optional volatile] (<string literal>[, optional parameters]) ;
</verb></tscreen>
or
<tscreen><verb>
- __asm__ (<string literal>[, optional parameters]) ;
+ __asm__ [optional volatile] (<string literal>[, optional parameters]) ;
</verb></tscreen>
<p>
-The first form is in the user namespace and is disabled by <tt><ref
+The first form is in the user namespace; and, is disabled by <tt><ref
id="option--standard" name="--standard"></tt> if the argument is not <tt/cc65/.
-The asm statement may be used inside a function and on global file level. An
-inline assembler statement is a primary expression, so it may also be used as
-part of an expression. Please note however that the result of an expression
-containing just an inline assembler statement is always of type <tt/void/.
+The <tt/asm/ statement can be used only inside a function. Please note that
+the result of an inline assembler expression is always of type <tt/void/.
-The contents of the string literal are preparsed by the compiler and inserted
-into the generated assembly output, so that the can be further processed by
-the backend and especially the optimizer. For this reason, the compiler does
-only allow regular 6502 opcodes to be used with the inline assembler. Pseudo
-instructions (like <tt/.import/, <tt/.byte/ and so on) are <em/not/ allowed,
+The contents of the string literal are preparsed by the compiler; and, inserted
+into the generated assembly output, so that it can be processed further by
+the backend -- and, especially the optimizer. For that reason, the compiler does
+allow only regular 6502 opcodes to be used with the inline assembler. Pseudo
+instructions (like <tt/.import/, <tt/.byte/, and so on) are <em/not/ allowed,
even if the ca65 assembler (which is used to translate the generated assembler
-code) would accept them. The builtin inline assembler is not a replacement for
-the full blown macro assembler which comes with the compiler.
+code) would accept them. The built-in inline assembler is not a replacement for
+the full-blown macro assembler which comes with the compiler.
Note: Inline assembler statements are subject to all optimizations done by the
-compiler. There is currently no way to protect an inline assembler statement
-from being moved or removed completely by the optimizer. If in doubt, check
-the generated assembler output, or disable optimizations.
+compiler. There currently is no way to protect an inline assembler statement
+-- alone -- from being moved or removed completely by the optimizer. If in
+doubt, check the generated assembler output; or, disable optimizations (for
+that function).
+
+As a shortcut, you can put the <tt/volatile/ qualifier in your <tt/asm/
+statements. It will disable optimization for the functions in which those
+<tt/asm volatile/ statements sit. The effect is the same as though you put
+<tt/#pragma optimize(push, off)/ above those functions, and <tt/#pragma
+optimize(pop)/ below those functions.
The string literal may contain format specifiers from the following list. For
each format specifier, an argument is expected which is inserted instead of
-the format specifier before passing the assembly code line to the backend.
+the format specifier, before passing the assembly code line to the backend.
<itemize>
<item><tt/%b/ - Numerical 8-bit value
<item><tt/%w/ - Numerical 16-bit value
<item><tt/%l/ - Numerical 32-bit value
- <item><tt/%v/ - Assembler name of a (global) variable or function
- <item><tt/%o/ - Stack offset of a (local) variable
+ <item><tt/%v/ - Assembler name of a global variable or function
+ <item><tt/%o/ - Stack offset of a local variable
<item><tt/%g/ - Assembler name of a C label
<item><tt/%s/ - The argument is converted to a string
<item><tt/%%/ - The % sign itself
</itemize><p>
-Using these format specifiers, you can access C <tt/#defines/, variables or
+Using those format specifiers, you can access C <tt/#defines/, variables, or
similar stuff from the inline assembler. For example, to load the value of
-a C <tt/#define/ into the Y register, one would use
+a C <tt/#define/ into the Y index register, one would use
<tscreen><verb>
- #define OFFS 23
- __asm__ ("ldy #%b", OFFS);
+ #define OFFS 23
+ __asm__ ("ldy #%b", OFFS);
</verb></tscreen>
Or, to access a struct member of a static variable:
<tscreen><verb>
- typedef struct {
- unsigned char x;
- unsigned char y;
- unsigned char color;
- } pixel_t;
- static pixel_t pixel;
- __asm__ ("ldy #%b", offsetof(pixel_t, color));
- __asm__ ("lda %v,y", pixel);
+ typedef struct {
+ unsigned char x;
+ unsigned char y;
+ unsigned char color;
+ } pixel_t;
+ static pixel_t pixel;
+ __asm__ ("ldy #%b", offsetof(pixel_t, color));
+ __asm__ ("lda %v,y", pixel);
+</verb></tscreen>
+<p>
+The next example shows how to use global variables to exchange data between C
+and assembler; and, how to handle assembler jumps:
+
+<tscreen><verb>
+ static unsigned char globalSubA, globalSubB, globalSubResult;
+
+ /* return a-b, return 255 if b>a */
+ unsigned char sub (unsigned char a, unsigned char b)
+ {
+ globalSubA = a;
+ globalSubB = b;
+ __asm__ ("sec");
+ __asm__ ("lda %v", globalSubA);
+ __asm__ ("sbc %v", globalSubB);
+ __asm__ ("bcs %g", jumpSubNoError);
+ __asm__ ("lda #$FF");
+ jumpSubNoError:
+ __asm__ ("sta %v", globalSubResult);
+ return globalSubResult;
+ }
+</verb></tscreen>
+<p>
+
+Arrays also can be accessed:
+
+<tscreen><verb>
+ static const unsigned char globalSquareTable[] = {
+ 0, 1, 4, 9, 16, 25, 36, 49, 64, 81,
+ 100, 121, 144, 169, 196, 225
+ };
+ static unsigned char globalSquareA, globalSquareResult;
+
+ /* return a*a for a<16, else 255 */
+ unsigned char square (unsigned char a)
+ {
+ if (a > 15) {
+ return 255;
+ }
+ globalSquareA = a;
+ __asm__ ("ldx %v", globalSquareA);
+ __asm__ ("lda %v,x", globalSquareTable);
+ __asm__ ("sta %v", globalSquareResult);
+ return globalSquareResult;
+ }
</verb></tscreen>
<p>
Note: Do not embed the assembler labels that are used as names of global
-variables or functions into your asm statements. Code like this
+variables or functions into your <tt/asm/ statements. Code such as this:
<tscreen><verb>
int foo;
- int bar () { return 1; }
- __asm__ ("lda _foo"); /* DON'T DO THAT! */
+ int bar (void) { return 1; }
+ ...
+ __asm__ ("lda _foo"); /* DON'T DO THAT! */
...
__asm__ ("jsr _bar"); /* DON'T DO THAT EITHER! */
</verb></tscreen>
<p>
-may stop working if the way, the compiler generates these names is changed in
-a future version. Instead use the format specifiers from the table above:
+might stop working if the way that the compiler generates those names is changed in
+a future version. Instead, use the format specifiers from the table above:
<tscreen><verb>
- __asm__ ("lda %v", foo); /* OK */
+ __asm__ ("lda %v", foo); /* OK */
...
__asm__ ("jsr %v", bar); /* OK */
</verb></tscreen>
<p>
+
<sect>Implementation-defined behavior<p>
This section describes the behavior of cc65 when the standard describes the
(to be done)
-<sect>Bugs/Feedback<p>
-
-If you have problems using the compiler, if you find any bugs, or if you're
-doing something interesting with it, I would be glad to hear from you. Feel
-free to contact me by email (<htmlurl url="mailto:uz@cc65.org"
-name="uz@cc65.org">).
-
-
-
<sect>Copyright<p>
This is the original compiler copyright:
freely, subject to the following restrictions:
<enum>
-<item> The origin of this software must not be misrepresented; you must not
- claim that you wrote the original software. If you use this software
- in a product, an acknowledgment in the product documentation would be
- appreciated but is not required.
-<item> Altered source versions must be plainly marked as such, and must not
- be misrepresented as being the original software.
-<item> This notice may not be removed or altered from any source
- distribution.
+<item> The origin of this software must not be misrepresented; you must not
+ claim that you wrote the original software. If you use this software
+ in a product, an acknowledgment in the product documentation would be
+ appreciated but is not required.
+<item> Altered source versions must be plainly marked as such, and must not
+ be misrepresented as being the original software.
+<item> This notice may not be removed or altered from any source
+ distribution.
</enum>
</article>
-