// UU  UU ZZZZZZ  8888   0000  // --------------------------------- //
// UU  UU     ZZ 88  88 00  00 // UZ80, a small Z80 macro assembler //
// UU  UU    ZZ  88  88 00  00 // written by Cesar Nicolas-Gonzalez //
// UU  UU   ZZ    8888  00  00 // since 2018-02-23 17:05 till today //
// UU  UU  ZZ    88  88 00  00 // --------------------------------- //
// UU  UU ZZ     88  88 00  00 // http://cngsoft.no-ip.org/uz80.htm //
//  UUUU  ZZZZZZ  8888   0000  // --------------------------------- //

Foreword
--------

UZ80 is a freeware Z80 assembler that aims to be both small and fast
while still providing valuable services such as macro instructions and
conditional assembly. Internally, it departs from full two-pass methods
and relies instead on assembling as much code as possible during the
first pass and writing down the lines making references to still unseen
symbols; these lines will be assembled when all symbols are known.

Software and documentation are provided "as is" with no warranty.

How to use
----------

UZ80 relies on the standard C library, it doesn't need other libraries
to run. Its command line syntax is as follows:

	UZ80 [-q|-v] [-D[label[=value]]] source [-o]target

	-q : quiet mode, no messages other than fatal errors are shown;

	-v : verbose mode, all messages are shown; -vv shows even more
	information, such as label and macro dumps;

	-Dlabel=value : defines a symbol named "label" whose value is
	"value";

	-Dlabel : shortcut for "-Dlabel=1";

	-D : shortcut for "-DDEBUG=1";

	source : the source file; must be followed by a target file;

	target : the target file; must follow a source file.

The assembly syntax itself is as follows:

	[LABEL[:]] [INSTRUCTION [PARAMETER[,PARAMETER ...]]]

Indenting is important: labels must begin on the first character of
each line and instructions start later in the line even when there are
no labels. Instructions are either those belonging to the Z80, or the
following pseudo instructions:

	org EXPRESSION : sets the assembly origin point at EXPRESSION;

	align EXPRESSION : aligns the current assembly point to the
	next address that is a multiplo of EXPRESSION;

	defb EXPRESSION... : defines a data block as a series of bytes
	separated with commas; strings within quotes can be used, too;

	defw EXPRESSION... : like "defb", but with 16-bit words and
	without strings;

	defd EXPRESSION... : like "defw", but with 32-bit double words;

	defs EXPRESSION : fills with zeroes the amount of bytes set by
	EXPRESSION;

	LABEL equ EXPRESSION / LABEL = EXPRESSION : creates a new label
	named LABEL whose value will be EXPRESSION;

	if EXPRESSION : assembles the next lines if EXPRESSION is
	nonzero (conditional assembly); "else" can follow, "endif"
	must follow;

	else : assembles the next lines if the current conditional
	assembly is zero; must follow "if", "endif" must follow;

	endif : ends the current conditional assembly; can follow
	"else", must follow "if";

	include "FILENAME" : includes the contents of another source
	file named FILENAME within the current assembly;

	LABEL macro [PARAM1[,PARAM2 ...] : defines a macro instruction
	named LABEL featuring the optional parameters PARAM1, PARAM2...

	endm : ends the definition of the current macro;

	end : stops assembling the current source file.

Expressions are similar to those used in C and in other assemblers:
integers (either decimal formatted as 1234 or 1234d, hexadecimal as
#1234, $1234, 1234h or 0x1234, octal as 1234o or binary as %10110111 or
10110111b) and symbols (case-insensitive; "$" stands for the current
address) can endure addition ('+'), substraction ('-'), multiplication
('*'), division ('/'), modulo ('%'), logical NOT ('!'), bitwise NOT
('~'), bitwise AND ('&'), bitwise OR ('|'), bitwise XOR ('^'), left
shift ('<<'), right shift ('>>') and several types of comparison ('<',
'<=', '='/'==', '<>'/'!=', '>=', '>'); by default, operation precedence
follows common rules such as additions and substractions taking place
after multiplications and divisions, but before comparisons, unless
parentheses are used to prioritise some operations over others.

Notice that "equ" and "macro" must include labels and thus need to
begin on the first character of the line.

An example of a macro with parameters is as follows:

	memcpy macro target,source,length
	 ld hl,source
	 ld de,target
	 ld bc,length
	 ldir
	 endm

Using it with "memcpy buffer,string,10" generates the following code:

	 ld hl,string
	 ld de,buffer
	 ld bc,10
	 ldir

Originally undocumented instructions such as SLL (Shift Left Logical)
and OUT (C),0 and parameters such as the high and low halves of IX and
IY (XH, XL, YH and YL respectively) are supported, as well as synonyms:

	DEFM/DB : DEFB
	DW : DEFW
	DD : DEFD
	DS : DEFS
	IXH/HX : XH
	IXL/LX : XL
	IYH/HY : YH
	IYL/LY : YL
	SHL : SLA
	SHR : SRL
	JP/CALL V/NV/S/NS,ADDR : JP/CALL PO/PE/M/P,ADDR
	PUSH REG1,REG2,REG3... : PUSH REG1 + PUSH REG2 + PUSH REG3 ...
	POP REG1,REG2,REG3... : ... POP REG3 + POP REG2 + POP REG1
	NOP NUMBER : NOP repeated NUMBER times

The pseudoinstructions "if" and "include" can be recursively nested;
however, too much nesting will cause a fatal error. Exit codes are
either 0 (success) or 1 (fatal error); errors will show a short message
stating the type of error and its location in the source.

Version log
-----------

20180321-2040: first public release. Succesfully compiles FROGALOT,
HIREHARE, BASKETCS and the CHIPNSFX player demo.

20180322-1930: second public release. Added instructions OUTD and OUTI
(synonyms of OTD and OTI) and fixed inconsistencies when using a macro
with fewer parameters than defined: BB4CPC and DUCKOUT compile.

20180326-1155: third public release. Added synonyms SUB/AND/XOR/OR/CP
A,PARAM for SUB/AND/XOR/OR/CP PARAM. Improper escape sequences raise
fatal errors. The Win32 binary is no longer packed with UPX.

20180408-1440: fourth public release. Buffers are now dynamically
allocated and reallocated, "out of memory" should happen only when no
more memory can be allocated. Several fixes in error handling: word
overflow no longer names itself as "byte out of range"; error messages
during final calculations are shown only once; opcodes relying on small
constants (BIT, IM and RST) perform consistent range checks.

20180414-1140: minor patch. Removed synonyms OTD and OTI. Code cleanup:
source is 48k, binary is 32k.

20180417-1920: fifth public release. Ditched the last remainder of AS80
compatibility: the symbol "$" means the current target address rather
than the current line's target; "defb nextline-$,nextline-$,nextline-$"
followed by "nextline:" is now equivalent to "db 3,2,1" rather than
"db 3,3,3". The tracker CHIPNSFX has been modified accordingly. Fixed
error messages of missing symbols in label definition expressions.

20180426-1030: sixth public release. Added synonyms LD BC/DE/HL,
BC/DE/HL for LD C/E/L,C/E/L+LD B/D/H,B/D/H. Fixed illegal commands LD
XL,L/H/(IX) and similar being accepted. INCLUDE swaps '/' and '\' if
required.

20180505-1200: seventh public release. Added synonyms LD BC/DE/IX/IY,
BC/DE/IX/IY for LD C/E/XL/YL,C/E/XL/YL+LD B/D/XH/YH,B/D/XH/YH. Added
the "no warranty" line to the foreword.

20180506-1230: minor patch fixing a bug in hexadecimal suffixes (1234h)
and adding octal and decimal suffixes (1234o and 1234d).

20180510-1255: minor patch fixing a bug in source paths with folders.

20180528-2020: minor patch fixing illegal command ADD IX/IY,HL being
accepted instead of ADD IX,IX/ADD IY,IY.

20180808-0946: eighth public release. Added "[" and "]" as indirect
addressing symbols: LD A,[HL] is equivalent to LD A,(HL). Bugfixes:
added dummy instructions "list" and "nolist" to ease compatibility;
command line parameter "-vv" returns the right exit code rather than
always 1, and "-oX" without source doesn't crash any longer; source
line "label:opcode" defines the label and assembles the opcode rather
than handling it as a very long label without any opcodes.
