...
Arithmetic operators
All basic arithmetic operators are supported. The following table shows them all. Result of example is shown in brackets for clarity of operator.
Operator symbol | Function | Example |
+ | Addition | 12+13 |
- | Unary minus, subtraction | -10, 12 - 45 |
* | Multiplication | 45 * 2 (90) |
/ | Division | 256 / 8 (32) |
> | Unary division by 256 | >1024 (4) |
% | Modulus | 256%8 (0) |
< | Unary modulus by 256 | <65000 (232) |
** | Power | 2 ** 7 (128) |
& | Binary AND | 255 & 7 (7) |
| | Binary OR | 128 | 64 (192) |
: | Binary NOR | 128 : 128 (0) |
^ | Binary XOR | 12 ^ 3 (15) |
~ | Unary Binary NOT | ~128 (127) |
<< | Binary left shift | 2 << 4 (32) |
>> | Binary right shift | 128 >> 4 (8) |
Arithmetic operators use the standard operator precedence, shown from highest to lowest:
0x $ @ ' (constant identifiers)
() []
~ > <
**
* / %
+- | ^ & : << >>
If you want to override the default operator precedence rules, use brackets () or []. The square bracket have been implemented as an alternative to avoid ambiguity with Z80 instruction mnemonics where indirect addressing uses the () as part of their syntax.
The # operator
This is not a real operator, though. It is only used as the first symbol in an expression to identify that this expression evaluates to a constant, i.e. containing no relocatable information. This feature may be necessary when you have to calculate a distance between two address labels without letting the assembler think it is a relocatable address. The assembler thinks that expressions containing address labels are relocatable items, which would create unwanted side effects during linking of object modules. However, since the assembler cannot see this as a constant expression, you have to force it as one.
Code Block |
---|
LD BC, end_relocator-relocator ; Mpm adds an ORG constant during linking LD BC, #end_relocator-relocator ; Mpm sees a constant expression |
Relational operators
With relational operators you may form logical expressions resulting in true or false conditions. The resulting value of a true expression is 1. The resulting value of a false expression is 0. These operators are quite handy when you need to perform complex logic for conditional assembly in IF-ELSE-ENDIF conditional assembly. The following relational operators are available:
= equal to
<> not equal to
< less than
> larger than
<= less than or equal to
>= larger than or equal to
! not
You may link several relational expressions with the binary operators AND, OR, XOR and NOT.
It is perfectly legal to use relational expressions in parameters requiring an arithmetic value. For example:
Code Block |
---|
LD A, [USING_IBM = 1] | RTMFLAGS ; use [] to ensure LD A,n instruction opcode |
Predefined assembler variables
Apart from declaring your own constants, Mpm has a few pre-declared constants that might become useful in your programs.
On occasional circumstances it may be necessary to use the current location of the assembler program counter in an expression e.g. calculating a relative distance. This may be done with the help of the $PC identifier. An example:
Code Block |
---|
errmsg0: DEFM errmsg1 - $pc - 1, "File open error" errmsg1: DEFM errmsg2 - $pc - 1, "Syntax error" errmsg2: |
$YEAR | 4-digit year value, eg. 2006 |
$MONTH | Month of the year, range is 1 to 12. |
$DAY | The day of the month, range is 1-31. |
$HOUR | Range is 0-23. |
$MINUTE | Range is 0-59. |
$SECOND | Range is 0-59. |
Directive reference
The MPM Module Assembler directives are used to manipulate the Z80 assembler mnemonics, generate data structures, variables and constants - even including binary files while code generation is performed.
As the name imply they direct the assembler to perform other tasks than just parsing and compiling Z80 instruction mnemonics. All directives are treated as mnemonics by the assembler, i.e. it is necessary that they appear as the first command identifier on the source line (NOT necessarily the first character). Only one directive is allowed per single source line. As with Z80 mnemonics, directives are case insensitive.
The following syntax is used to describe the directives:
<> defines a syntactic entity, i.e. a number, character or string.
{} defines a repetition of a syntactic entity.
[] defines an option that may be left out.
ALIGN
Align (or zero-pad) a specified number of bytes relative to the current PC. Argument value range = 1-16. For example use ALIGN 4 to ensure that the new PC is located at a module address that is aligned in 4 byte entities. Another example would be to use ALIGN 2 to make sure that the next PC address is located at an even address. ALIGN only aligns addresses on the current module compilation - not on the entire scope of the linked modules. If you want to align all linked modules to even adresses, use an ALIGN at the end of each module. |