System information
Unfortunately, the 8564-VIC chip cannot handle a clock frequency of 2 MHz, which results in garbage on the
screen. It may therefore be a good idea to blank the screen by setting bits 4 and 7 of register $D011 to 0 before
changing to 2 MHz in order not to see the garbage on the screen. Another alternative is to use raster interrupts
so that 2 MHz is only used while the electron beam is outside of the visible screen, i.e. when it is in the lower or
upper border. This method is for example used in the game Test Drive II when run in C64 mode on a C128. The
advantage of this method is that characters or graphics will still be visible while the disadvantage is that the
clock frequency will not be 2 MHz all the time.
The 80-column 8563 chip (which requires an RGBI monitor) can handle a clock frequency of 2 MHz.
The 2 MHz mode can also be used in Commodore 64 mode on the Commodore 128. The same limitation applies
as in Commodore 128 mode, i.e. the VIC chip cannot handle such a high frequency, which results in garbage on
the screen.
Z80 CPU
In addition to the 8502 CPU, the C128 also contains a Z80 CPU. The Z80 is used in CP/M mode except at Kernal
routine calls where the 8502 is temporarily switched in in order to avoid having duplicate Kernal routines in the
ROM. The C64/C128 BASIC and Kernal only use the 8502 CPU but although it is very rarely done it is possible to
write a program that uses the Z80 from C128 mode. The following paragraphs give a brief description about how
to do this. How to program in CP/M mode is not covered here.
Because of the pipelined architecture of the 8502, a 1 MHz 8502 is approximately comparable in speed with a 4
MHz Z80. However, on the C128, the Z80 only runs at 4 MHz half the time giving an effective clock speed of 2
MHz. This means that the Z80 is only about half as fast as the 8502 (only about a fourth as fast when the 8502
is in 2 MHz mode). Despite of this, there might be situations where you would want to use the Z80 from C128
mode. One reason would be if you are short of memory space and speed is not that important. This is because
the Z80 has a bigger and more powerful instruction set than the 8502 and it is therefore probably sometimes
possible to do things using less memory on the Z80 (I haven't made any comparisons so I can't say this with
certainty). There are for example instructions for 16-bit arithmetics and for copying blocks of data. However, a
drawback is when you want to do accesses to I/O registers because that requires more instructions on the Z80
than on the 8502 since you have to use the IN and OUT instructions. See the following example:
LD A,0 ;PUT 0 (BLACK) IN ACCUMULATOR LD BC,$D020 ;PUT $D020 IN REGISTERS B AND C, NOTE HOW THE
Z80 CAN USE 2 8-BIT REGS AS 1 16-BIT REG OUT (C),A ;SET BORDER COLOR, OUT MUST BE USED RATHER
THAN LD FOR I/O REGS TO AVOID BLEED-THROUGH TO UNDERLYING RAM
Another reason would be if you are more familiar with the Z80 than with the 8502, for example if you have
programmed on the Sinclair ZX Spectrum before. A third reason would be if you simply think it would be cool to
do something that not so many people have done before. The last reason was the one that appealed most to
me ;) .
How do you switch in the Z80? In RAM bank 0, there is an 8502 routine at $FFD0 to switch to the Z80 and at
$FFE0 there is a Z80 routine to switch in the oposite direction. The routines have been copied there by the Z80
boot ROM at start-up. When the routine at $FFD0 is called, the Z80 wakes up where it was switched out in the
routine to switch in the opposite direction (at $FFEE to be precise). Where the Z80 wakes up, there is a RST 8
instruction, which causes CP/M to boot. If you want to run your own Z80 program instead, it is a good idea to
change the instruction to a JP instruction to jump to your own code.
The 8502 routine at $FFD0 sets the RAM bank to RAM bank 0. In RAM bank 0 with the Z80 enabled, the Z80
ROM (containing reset and CP/M boot code) is seen at address $0000-$0FFF. There is a trick to avoid this.
According to most literature, RAM bank 2 is indentical to bank 0. However, this is not true when the Z80 is
active. If you select RAM bank 2, you will instead get RAM at $0000-$FFFF so when you write your own Z80
programs it might be a good idea to change the routine at $FFD0 to set RAM bank 2 instead of RAM bank 0. You
can of course also select RAM bank 1 but since Power Assembler uses that a lot, it might be difficult.
When the Z80 processor is active with the MMU set so that there is I/O at $D000-$DFFF and RAM bank 0 or 2 in
the rest of the 64 kB of address space, color RAM is at $1000-$13FF and NOT at $D800-$DBFF where it is on the
C64 and on the C128 with the 8502 active. $1000-$13FF is a part of the I/O space so just as for $D000-$DFFF,
"OUT (C),A" should be used to write a byte and "IN A,(C)" to read a byte.
Of the three interrupt modes that the Z80 supports, the C128 supports the two modes IM 1 and IM 2 (not IM 0).
Personally, I think IM 1 is easiest to set up. With IM 2 you have to fill 257 bytes with the same 16-bit address to
the interrupt routine. You also have to set the I register to the base of the 257-bytes block. With IM 1, on the
other hand, you know that the Z80 will start executing at $0038 when the interrupt occurs. Don't forget that with
the Z80 you have to enable interrupts again in the interrupt routine (using EI). Otherwise, you won't get any
more interrupts.
There are some things you can only do with the 8502 but not with the Z80. There is an NMI input on the Z80