Chapter 8.
C & S T E M E N Li
P R O C E D U r s
For programming in Assembler Z80,
Rom (ROM) ZX-SPECTRUM is a valuable repository of ready-made
and well-functioning procedures native. Some of them may be a
successfully used with the level of the Basic
creating additional features not available in another way. We
restrict ourselves description of critical system processes.
8. 1 Work with sound
In the ZX-SPECTRUM speaker can be excited
in two ways.
BEEPER # 03B5 (949) This procedure requires 2 parameters.
The register is placed DE the duration of sound, and the
register HL - frequency. These values, before placing them in
the registers, require the prior conversion. Suppose we want to
get the tone with a frequency and duration of F T. Then, DE is
loaded F * T, a in the HL 437500/F-30, 125. Avoid these
calculations can be calling another procedure.
BEEP # 03F8 (1016) It requires a set
time and frequency of sound in normal units. These parameters
are passed BEEP by placing them in a stack calculator. BEEP
takes them out on their own, serves are necessary
transformations and causes BEEPER.
BEEPER little better instructions ZX-BASIC BEEP with the
view that it not subject to restrictions on the parameter
values. data are controlled in time transformations performed
BEEP. In time generation of sound all interrupts are
prohibited. The last statement before BEEPER implementation of
RET is EL.
8. 2 Work with a tape recorder
As headers and data blocks are recorded on tape by the same
procedure:
SAVE BYTES # 04C2 (1218). Registers DE
must be on the length of zapisyvemogo block
in the IX - the address of the first byte, and in buffer A -
recordable unit:
TYPE 0 - TITLE
TYPE 255 (# FF) - UNIT DATA
In principle, they differ in that the title is preceded by a
longer entrance signal (about 5 seconds) than
block of data (about 2 seconds). User
may use other values
type between 0 and 255 for type designation
block. This is useful in designating different
types of data in special applications.
Such blocks are ignored instructions LOAD
in reading (not displayed on them
no data), and some programs
copying.
Standard header always consists of
17 bytes of data:
1 byte - the type of data block:
0 - BASIC Program;
1 - a numeric array;
2 - a landmark array;
3 - a set of bytes.
2 .. 11 bytes - the name length of 10 bytes.
Allowed all the codes from 0 to 255. If
the name is shorter than 10 bytes, then it is padded with
blanks.
12, 13 bytes - length of the block, the next
the header.
14-17 bytes - depends on the type of set:
- For type 0:
14-15 bytes - number of line start-up, refusal to start is
signaled by the value 32,767 more (# 7FFF).
16-17 bytes - the length of the program without
field variables.
- For types 1 and 2 are only
15 bytes for the job (odnoliternogo) name
zapisyvemogo array (the name under which he
stored in variables.
- For Type 3:
14-15 bytes - starting memory address, in
which is a lot at the time of writing.
The above header format must be maintained only for those
cases where the described Blocks must be read instruction LOAD.
Reading the written instruction sets is:
LOAD BYTES # 0556 (1566)
As well as for SAVE BYTES. Before calling in a couple of
puts the length of the retrieved DE block in the IX - starting
memory address for recording unit, and A - the type of the
retrieved set. Additionally, still need to set a pointer to C
instruction SCF. Call this procedure with a null pointer C
eliminates the verification of the block (similar to the
command VERIFY). Possible Error reading or verification
signaled zeroing pointer C after leaving the subroutine. Normal
execution is signaled by the installation procedure C = 1.
8. 3 Displaying and Printing
Displaying the single character code
which is in the buffer at the top
or bottom of the screen and the printer is performed by the
same procedure. Before her call to open the appropriate channel
using the procedure:
CHAN OPEN # 1601 (5633).
In the buffer must be a sign
desired channel: 1-for "K", 2 for
"S" and 3 for the "P". This channel will be open
as long as we do not close.
If after that to issue a command assembler:
RST # 10,
then it will print a single character,
located in buffer A, the selected channel. Program below
illustrates the application of RST # 10. Its implementation
tantamount to the team:
PRINT FLASH 1; AT5, 3; "X"; # 3; "A".
LD A, 2; open
CALL CHAN_OPEN; channel "S"
LD A, # 12, the character code FLASH
RST # 10;
LD A, 1; argument FLASH
RST # 10;
LD A, # 16; character code AT
RST # 10;
LD A, 5; arguments AT
RST # 10;
LD A, 3;
RST # 10;
LD A, # 58; code "X"
RST # 10;
LD A, 3; open
CALL CHAN_OPEN; channel "P"
LD A, # 41, the character code "A"
RST # 10;
RET; exit podprog
FRAMEWORK
Note that the sign "A" will be sent to the printer buffer, and
in fact will Printed on paper only after the buffer is full,
transfer to the buffer line ending character (13) or call:
COPY_BUFF # 0ECD (3789).
This example shows that the shipment
chain of characters, one character can
be extremely tedious. Easier to apply
procedure:
PR_STRING # 203C (8252).
It prints a string of characters, whose address is given in
the registers of DE, the length of BC. Before her call to open
the appropriate channel. If the printable characters do not
specify color, they are set based on variables FTTR_T, MASK_T,
and and odd bits P_FLAG.
Print numbers more difficult, so
as is necessary to translate a binary number in the sequence of
characters its decimal representation. All the necessary
calculations and executes printing procedure:
PRINT_FP # 2DE3 (11,747).
It removes from the stack calculator 5
bytes, counting their numbers in the format adopted in the
ZX-BASIC. Then prints them based on system variables
determining the color, position, and so on. Methods placement
of numbers on the stack, we stipulate below.
In the case of natural numbers from 0 to 9999
You can use a faster procedure:
OUT_NUM1 # 1A18 (6683).
It prints the number contained in the BC
A 4-fields. Outputting first necessary
number of spaces, ZX-SPECTRUM uses this
procedure to print line numbers in the program listing.
8. 4 screen graphics
To draw on the screen we have analogues procedures PLOT,
DRAW and CIRCLE.
PLOT_SUB # 22E5 (8933)
- Allows you to display on the screen, single point with
coordinates (X, Y). Before calling to place X in C and Y in B.
PIXEL_ADD # 22AA (8874)
- After entering in the BC values (Y, X)
and call this function, we get the registers HL byte address,
which describes this point on the screen. In addition to the
buffer fills the X MOD 8, specifying what kind of bit of the
byte in question.
DRAW_1 # 2477 (9335)
- Captures the stack calculator
X and Y, and then draws the appropriate
segment. Coordinates are selected from the PLOT
system variables.
DRAW_3 # 24BA (9402)
- To draw a similar interval
this procedure, you must specify ABS Y ->
B, ABS X -> C, SGN Y -> D SGN X -> E.
DRAW_ARC # 2394 (9108)
- Draws an arc fragments. Options X, Y,
Z for this procedure must be passed
through a stack calculator. Z is placed
top of the stack.
CIRCLE_1 # 2320 (9005)
- Draws a complete circle with center
(X, Y) and radius Z. All options also
should be placed in a stack calculator.
NOTE: The above procedure
modify registers H, L (see the chapter "System Errors").
Following the withdrawal of the desired image on the screen,
it can be printed out. Analogue
How-COPY is the procedure:
COPY # 0EAC (3756) - This procedure copies the printer 22
top rows.
Parameters of all the above procedures
subject to the same restrictions as the corresponding commands
in BASIC.
8. 5 Cleaning and moving screen
CLS # 0D68 (3435)
- The basic procedure for cleaning the screen.
Ee action is analogous to Directive
with the same name.
CLS_LOWER # 0D6E (3438)
- Clean the bottom of the screen. She
acts on the entire bottom of the screen regardless of its
current size, and simultaneously sets the height of two lines.
Initialized and system variables and DF_CL SPOSNL, determining
the position of the cursor.
CL_LINE # 0E44 (3652)
- Cleaning up, starting with the bottom edge of the screen,
a specified number of rows. The number of rows contained in the
register B.
Before calling these procedures should be
Make sure the channels are open. Two
first of them left after the canal
"K" open. Erasing a color screen
established on the basis of system variables BORDCR to the
bottom of the screen, and also ATTR_P and MASK_P to the top
after what their content is copied in ATTR_T and
MASK_T.
CL_SC_ALL # 0DFE (3582)
- Moves the contents of the entire screen
(24 full lines) one line up
(Top row disappears.) It can be accessed directly from BASIC,
because it does not require parameters.
CL_SCROLL # 0E00 (3584)
- After entering in the register B of
row-1 for the shift (at least 2), this procedure will advance
by one line as lines as you want without touching above.
Consequently, we can be at the top of the screen image or text
that are not destroyed by a shift by one line.
Applying these procedures must be remembered
that will rise up as the required attributes at the bottom of
the screen.
8. 6 read keyboard
Information from the keyboard is most advantageous
remove c system variable LAST_K.
Check the condition of the fifth bit variable
FLAGS, we can determine is pressed or not pressed another
button (1-pressed New, 0 is not pressed yet none since the
reset of this bit). After reading the code buttons, reset this
bit, we provide yourself the opportunity to know, modified,
Do More content LAST_K or not. It acts only when the masked
interrupt mode 1. It is in this case, the ZX-SPECTRUM
automatically calls the procedure 50 times a second:
KEYBOARD # 02BF (703)
She watches all of the keyboard, identifying the right
combination of keys, puts the read code to the clipboard, as
well as variable KASK_K and establishes the fifth bit FLAGS.
Interpretation of the pressed key will be depend on three
system variables. We first checked the contents of MMODE,
regarded as a signed integer in the code
two's complement:
MODE-1 <0 represents the cursor K, L, or
C
MODE-1 = 0 represents the cursor E
MODE-1> 0 denotes a cursor cursor K G
of L and C differs by a third bit variable FLAGS. 0 means that
K, and 1 indicates L or C. The third bit FLAGS
finally determines whether the cursor
L (0) or C (1). This procedure does not expect
keystroke.
So that regardless of the state of the cursor
clarify whether a particular key is pressed, more productive
can be a direct survey of the keyboard with the help of How-IN.
Here we proceed as As in the case of a function with the same
name in BASIC.
8. 7 Calculator
Various actions on the floating-point numbers are performed
using a large set of procedures that occupy space on the ROM #
2F9B (12187) to # 3860 (14,445). The calculator is called the
instruction RST # 28, which performs the transition to Address
# 3358 (131457).
The basis of the calculator is 66
different procedures, performs a set of basic operations on a
stack calculator. Priorities for their implementation is given
chain bytes, placed directly behind the team RST # 28. The end
of this chain is always marked by a byte with a value of # 38
(56).
As required, we restrict the operations that allow to
perform various numerical calculations. Assume that the top
stack are the numbers ... Z, X, Y.
_______________________________________
| | | |
| Then. | | The state stack |
|-------| Operation | after |
| DEC | HEX | | operation |
|---|---|----------|--------------------|
| 1 | # 01 | change | ... Z Y X |
| | | Items | |
| 3 | # 03 | subtraction | ... Z XY |
| 4 | # 04 | multiplication | ... ZX * Y |
| 5 | # 05 | division | ... Z X / Y |
| 6 | # 06 | degree | ... Z X ** Y |
| 15 | # 0F | addition | ... Z X + Y |
| 27 | # 1B | change | ... Z XY |
| | | Mark | |
| 31 | # 1F | sine | ... Z X SIN Y |
| 32 | # 20 | cosine | ... Z X COS Y |
| 33 | # 21 | tan | ... Z X TG Y |
| 34 | # 21 | sine | ... Z X ASN Y |
| 35 | # 23 | arccosine | ... ZX ACS Y |
| 36 | # 24 | arctangent | ... ZX ATG Y |
| 37 | # 25 | log | ... Z X LN Y |
| | | Natural. | |
| 38 | # 26 | Exhibitor | ... ZX EXP Y |
| 39 | # 27 | integer | ... Z X NT Y |
| | | Of | |
| | | Number | |
| 40 | # 28 | root | ... Z X SQR Y |
| | | Square. | |
| 41 | # 29 | number sign | ... ZX SGN Y |
| 42 | # 2A | absolute | ... ZX ABS Y |
| | | Value | |
| 49 | # 31 | copying-| ... Z X Y Y |
| | | Of the stack | |
| 50 | # 32 | N MOD M | ... Z residues. Privacy |
| 52 | # 34 | append | ... Z X Y D |
| | | Stack | |
| 56 | # 38 | end | ... Z X Y |
| | | Payments | |
| 88 | # 3A | INT (Y +0.5) | ... Z X INT (Y + .5) |
| 160 | # A0 | Append 0 | ... Z X Y 0 |
| 161 | # A1 | Append 1 | ... Z X Y 1 |
| 162 | # A2 | Append | ... Z X Y 0.5 |
| | | 0.5 | |
| 163 | # A3 | Append | ... Z X Y PI / 2 |
| | | PI / 2 | |
| 164 | # A4 | Append | ... Z X Y 10 |
| | | 10 | |
|___|___|__________|____________________|
As an example of using the calculator
calculate the value of 1. 5 * SIN (X)
+ X ** 2 * COS (X * PI / 2). Assume that the value
X is on top of the stack. Accommodation for
construction of RST # 28 to read the first byte
Speakers will:
_______________________________________
| | |
| Byte | Condition stack |
|-----|---------------------------------|
| # 31 | X X |
| # 31 | X X X |
| # 31 | X X X X |
| # A3 | X X X X PI / 2 |
| # 04 | X X X X * PI / 2 |
| # 20 | X X X COS (XPI / 2) |
| # 04 | X X X * COS (X * PI / 2) |
| # 20 | X X * X * COS (X * PI / 2) |
| # 04 | X * X * COS (X * PI / 2) X |
| # 01 | X * X * COS (X * PI / 2) SIN (X) |
| # 1F | Append 1.3 (5 bytes) |
| # 34 | 1 |
| # F1 | 2 |
| # 26 | 3 |
| # 66 | 4 |
| # 66 | 5 |
| # 66 | X * X * COS (X * PI / 2) SIN (X) 1.3 |
| # 04 | X * X * COS (X * PI / 2) 1.3 * SIN (X) |
| # 0F | X * X * COS (X * PI / 2) +1.3 * SIN (X) |
| # 38 | end computing |
|_____|_________________________________|
Explanation requires an entry in the calculator stack data
as a sequence bytes following immediately behind the # 34.
Bytes # F1 # 26 # 66 # 66 # 66 represent the number of
2 ** 113 * 0. 13 rather than 0. 13. This is due to
interpreting them as numbers in the truncated
record. The scheme is as follows:
- First byte is divided by # 40 (64) and as
the exponent is taken:
the remainder of this division, plus # 50 (if
it is different from 0), or the next byte plus
# 50 (if the remainder is 0);
- Integral part of the division of (0, 1, 2, 3)
plus 1 determines how much demanded
bytes for the mantissa. Missing up to 5 bytes
filled with zeroes.
In our example, # F1 (241) divided by the
# 40 (64) gives the residue # 31 (49), as well as
kiss part 3. This means that the exponent of our number is
# 31 + # 50 = # 81 and requested that all 4 bytes
mantissa. In this system, the number 0 is
submission # 40 # B0 # 00, since 0 divided
at # 40 gives a remainder equal and integral part
0. Then becomes the second byte + # 50 or
# B0 + # 50 = 00 (all these calculations on the individual
bytes being modulo 256) and is given by
only the first byte of mantissa. The remaining bytes
(5) supplemented by zeros. In turn,
number 10 has the representation
# 40 # 80 # 00 # 0A.
Glyph # 34 allows you to place the numbers in
Throughout the program in assembly language. However,
often required to put on the stack parameters
instructions or values calculated in
program. To do this meant a lot
ancillary procedures. They allow
as extracting value from the stack and
Writing to the different numbers:
STK_TO_BC # 2307 (8967)
- The next two for a number (a 5-
byte representation) are extracted from
stack and inserted into registers B and C. Their
values should be in the range from -255
255. Otherwise the refund in
BASIC with the message B (to be completed
User RST # 8). This procedure can
applied to negative numbers. Their
characters are returned in registers D and E. Numbers derived
from the stack, rounded to nearest whole number.
STK_TO_A # 2314 (8980)
- A procedure similar to the previous one, with
except that the stack is removed
only one number, and after rounding up
placed in a buffer. Sign of returning to the register C.
STACK_FETCH # 2BF1 (11249)
- This procedure removes from the stack, all
number (5 bytes) and places it in the registers A, E, D, C, B.
FP_TO_BC # 2DA2 (11682)
- Number of stack is rounded to the nearest whole number and
mix of register BC. The sign is determined by the number of
index Z (0 - for negative) if the value in the stack exceeds
the maximum 65535, then the pointer is set to 1 and
this is the only reaction to error (return to the ZX-BASIC is
not happening).
STK_STORE # 2AB6 (10934)
- This procedure places the top of the stack
5 bytes of the registers A, E, D, C, B. Number
1.3 (# 81 # 26 # 66 # 66 # 66) can add to the stack
calculator 2 ways (note that the second method allows you to
save 3 bytes:
LD A, # 81 RST # 28
LD DE, # 6626 or DEFB # 34
LD BC, # 6666 DEFB # F1
CALL # 2AB6 DEFB # 26
DEFB # 66
STACK_A # 2D28 (11560)
- The value of register A periodically
entered into the stack in a 5-byte representation.
STACK_BC # 2D2B (11563)
- This procedure is similar to the previous
but the stack is stored with the register number of BC.
After completion of payments calculator
Registers HL locates the address of the first
5 bytes are at the top of the stack. When you work with a
calculator to cares about the related work with a stack. It
should also be remembered that the procedure PRINT_FP removes
from the stack the printed number. At the end of the present
challenge of the program Native pseudorandom generator
numbers:
LD A, # A5
CALL STACK_A
RST # 28
DEFB # 2F
DEFB # 1D
DEFB # 38
RET
This program puts the next pseudorandom number in the top of
the stack and updates the system variable SEED.
8. 8 Additional system procedures
SET_MIN # 16B0 (5808)
- Generates a global clean working areas of BASIC, as well
as stack calculator. It modifies the system
variables indicating the relevant
memory area. Physically overwritten only those bytes that are
recorded Indices the end of the field.
MAKE_ROOM # 1655 (5717)
- Calling it should be in registers HL
give the address of the start byte extension block
and BC block size. The procedure itself
establishes what the system variables
must be modified in the case
need to modify them. Consequently, it allows insertion into an
existing program in BASIC or in the region new variables,
operators, variables and etc..
RECLAIM_2 # 19E8 (8168)
- Contact the previous function. Here in
HL recorded address of the first byte that
should be removed, and the BC size erase block. Also, as
before, the relevant system variables will be automatically
modified.
CLFAR_BUFF # 0EEF (8815)
- How to clean printer buffer and
modifies the related system variables.
LINE_ADDR # 196E (6510)
- Finding the row address with the specified
number in the program in BASIC. Before calling the number
recorded in the HL searched line. The output of the HL, we have
addressed this line or the first with a large number. If
line with a given number is, it is
indicated by the pointer Z.
FREE_MEM # 1F1A (7962)
- Identification of free memory for BASIC, ie, between
STKEND and RAMTOP. Registers HL and BC contain the same
a negative number represented in the code
additions to 2, is the difference between
STKEND +80 and SP (stack pointer processor
Z80).
BREAK_KEY # 1F54 (8020)
- Her call to verify the rollover and . If
they are pressed, the pointer C reset.