mirror of
https://github.com/problemkaputt/problemkaputt.github.io.git
synced 2024-05-12 09:44:52 -04:00
3173 lines
143 KiB
Plaintext
3173 lines
143 KiB
Plaintext
Portar Specifications
|
||
---------------------
|
||
|
||
Contents
|
||
--------
|
||
|
||
MSX Hardware I/O Addressing
|
||
--> I/O Port Summary
|
||
--> Memory
|
||
--> Peripheral Interface
|
||
--> Video Display Processor
|
||
--> Sound Generator
|
||
--> Cartridge Memory Mappers
|
||
--> Floppy Disk Controller
|
||
--> Real Time Clock
|
||
--> RS 232 Interface
|
||
--> Kanji ROM
|
||
--> Special I/O Registers
|
||
|
||
Other MSX related Info
|
||
--> Z80 CPU Specifications
|
||
--> Different MSX Models
|
||
--> External Connectors
|
||
--> Data Structures and Formats
|
||
--> Other DOCs
|
||
--> About this Document
|
||
|
||
About this Document
|
||
-------------------
|
||
|
||
Portar Doc Version 1.7, last updated 21st March 2001 by Martin Korth.
|
||
This document describes the I/O Map of MSX computers, attempting to supply a
|
||
very compact and mostly complete document about MSX1 and MSX2 hardware. It
|
||
does not include information about the MSX firmware and operating systems,
|
||
such like BIOS, BASIC, BDOS, MSXDOS, or CP/M related functions. Written by
|
||
MAYER (1991-1995) and Martin Korth (1999-2001).
|
||
|
||
First Generation 1991-1995 by MAYER of WC HAKKERS
|
||
MAYER's SV738 X'press I/O MAP version 1.5. Thanks to Henrik Gilvad (Denmark)
|
||
for info about the MSX-2 MVDP and the MSX-2 ROMs, to Pal F Hansen (Norway) for
|
||
VRAM info and to Jonas Lindstroem (Sweden) for some MVDP info.
|
||
|
||
Second Generation 1999-2001 by Nocash/Martin Korth
|
||
Thanks to Enrique Sanchez for his collection of various docs, to Manuel Pazos
|
||
for answering many questions and for V9958 specs, to Sean Young for his
|
||
MEGAROMS doc and some TMS9918A details, to Konami Man and Ascii for MSX2
|
||
Technical Handbook, to Zelly of Mayhem for his V9958 summary, to Tomas
|
||
Karlsson for WD1793 FDC specs, to Ascat/Takamichi for Kanji description, and
|
||
to MAYER for the original doc & for comments about the updated version.
|
||
|
||
Other Formats and Updates and Help Wanted
|
||
This text is available in .TXT format (raw 7bit Ascii), and .HTM format
|
||
(HTML). The .HTM version includes simple formatting for chapters, hyperlinks,
|
||
and bold headlines.
|
||
http://www.work.de/nocash/portar.txt
|
||
http://www.work.de/nocash/portar.htm
|
||
Some sections in this doc are marked by question marks, if you can confirm or
|
||
explain these parts, or if you know additional information, or if you find any
|
||
information to be incorrect or incomplete, please drop a note to Martin Korth
|
||
(http://www.work.de/nocash/email.htm).
|
||
|
||
Copyright
|
||
This text may not be sold, or included in commercial software/hardware or
|
||
firmware packages, or used or duplicated for other commercial purposes without
|
||
the authors permission. You may copy and spread this document for
|
||
non-commercial purposes as long as you leave this page intact and without
|
||
changes.
|
||
|
||
I/O Port Summary
|
||
----------------
|
||
|
||
I/O Ports
|
||
Most internal MSX hardware is accessed by I/O instructions. In most (or all)
|
||
cases only the lower 8 bits of the I/O addresses are relevant.
|
||
Port R/W Chip/Name/Function
|
||
00-3F NC Free for User
|
||
40-7B NC Reserved
|
||
7C ? MSX MUSIC YM2413/OPLL (FM-PAC,FM-PAK,MSX2+) Index
|
||
7D ? MSX MUSIC YM2413/OPLL (FM-PAC,FM-PAK,MSX2+) Data I/O
|
||
7E-7F NC Reserved
|
||
80 R/W RS232 I8251 (ACIA) Data
|
||
81 R/W RS232 I8251 (ACIA) Status/Command
|
||
82 R RS232 Status for CTS,Timer/counter2,RI,CD
|
||
82 W RS232 Interrupt mask register
|
||
83 R RS232 ?Clock 0,1,2 read?
|
||
83 W RS232 ?Receive ready interrupt enable?
|
||
84 R/W RS232 I8253 (Baud gener.) Counter 0 Receive clock
|
||
85 R/W RS232 I8253 (Baud gener.) Counter 1 Transmit clock
|
||
86 R/W RS232 I8253 (Baud gener.) Counter 2 Used by programs
|
||
87 W RS232 I8253 (Baud gener.) Mode register
|
||
88 ? ?Modem enable?
|
||
88-8B R/W,W External VDP 9938 adaptor for MSX1 (similiar to Port 98-9B)
|
||
8C-8D ? Reserved for modem
|
||
8E-8F NC Reserved
|
||
90 R ULA5RA087 Centronic BUSY state (bit 1=1)
|
||
90 W ULA5RA087 Centronic STROBE output (bit 0=0)
|
||
91 W ULA5RA087 Centronic Printer Data
|
||
92-97 NC Reserved
|
||
98 R/W 9918,9929,9938,9958,9978 VRAM Data Read/Write
|
||
99 R 9918,9929,9938,9958,9978 VDP Status Registers
|
||
99 W 2nd Byte b7=0: 99X8 VRAM Address setup
|
||
99 W 2nd Byte b7=1: 99X8 VDP Register write
|
||
9A W MVDP (MSX2) 9938,9958 Color Palette Register (2 bytes)
|
||
9B W MVDP (MSX2) 9938,9958 Register data
|
||
9C-9F NC Reserved
|
||
A0 W I AY-3-8910 PSG Sound Generator Index
|
||
A1 W I AY-3-8910 PSG Sound Generator Data write
|
||
A2 R I AY-3-8910 PSG Sound Generator Data read
|
||
A3-A7 NC Reserved
|
||
A8 R/W I 8255A/ULA9RA041 PPI Port A Memory PSLOT Register (RAM/ROM)
|
||
A9 R I 8255A/ULA9RA041 PPI Port B Keyboard column inputs
|
||
AA R/W I 8255A/ULA9RA041 PPI Port C Kbd Row sel,LED,CASo,CASm
|
||
AB W I 8255A/ULA9RA041 Mode select and I/O setup of A,B,C
|
||
AC-AF NC Reserved
|
||
B0-B3 ? External 8255 (SONY DataRamPack)
|
||
B4 W RP 5C01 (Not in 738) RTC Register select
|
||
B5 R/W RP 5C01 (Not in 738) RTC data
|
||
B6-B7 NC Reserved
|
||
B8-BB ? SANYO Light pen interface
|
||
BC-BF ? VHD control
|
||
C0-C1 ? MSX audio (used in Music Module cartridge by Philips, OPL1)
|
||
C2-C7 NC Reserved
|
||
C8-CF ? MSX Interface (??)
|
||
D0-D7 ? External Floppy Disk Controller
|
||
D8h W Kanji ROM Select Class 1 Code (lower 6 bits)
|
||
D9h W Kanji ROM Select Class 1 Code (upper 6 bits)
|
||
D9h R Kanji ROM Read Class 1 Data (32 bytes)
|
||
DAh W Kanji ROM Select Class 2 Code (lower 6 bits)
|
||
DBh W Kanji ROM Select Class 2 Code (upper 6 bits)
|
||
DBh R Kanji ROM Read Class 2 Data (32 bytes)
|
||
DC-F4 NC Reserved
|
||
E5-E7 ? MSX-Engine chip (MSX2/2+/TurboR) ???
|
||
F5 W System Control (used to disable internal I/O ports)
|
||
F6 ? colour bus
|
||
F7 R/W Audio/Video control
|
||
F8-FB NC Reserved (But somehow accessed by MSX2 BIOS ???)
|
||
FC R/W Memory Mapper (RAM bank for 0000-3FFF)
|
||
FD R/W Memory Mapper (RAM bank for 4000-7FFF)
|
||
FE R/W Memory Mapper (RAM bank for 8000-BFFF)
|
||
FF R/W Memory Mapper (RAM bank for C000-FFFF)
|
||
|
||
Memory mapped I/O
|
||
Most external hardware (and most external and internal disk controllers) are
|
||
accessed by memory mapped I/O, ie. by LD commands rather than by IN and OUT
|
||
commands. Common memory mapped I/O addresses are:
|
||
DISK:7FXX Floppy Disk Controller
|
||
DISK:BFXX Floppy Disk Controller
|
||
CART:XXXX Cartridge Memory Mappers
|
||
CART:98XX Cartridge SCC (Sound Custom Chip)
|
||
SLOT:FFFF Secondary Slot (select DISK ROM or MAIN RAM in a PSLOT)
|
||
To access these I/O 'Ports', the respective memory area must be selected into
|
||
memory by the PSLOT register, and then data can be written (or read in some
|
||
cases) to (or from) the memory addresses.
|
||
|
||
Memory
|
||
------
|
||
|
||
Port A8 Primary Slot Register (PPI Port A, PSLOT) (Read/Write)
|
||
Port FC-FF Memory Mapper RAM page select (Read/Write)
|
||
Mem. SLOT:FFFF Secondary Slot Register (Read Inverted/Write)
|
||
Mem. CART:XXXX Cartridge Memory Mappers
|
||
|
||
Memory Map example for a diskless MSX1 machine
|
||
A typical MSX1 model includes 32K ROM, and 8K, 16K, 32K, or 64K RAM. External
|
||
RAM or ROM Expansions/Games, or Disk Controller (with 16K DISK ROM) could be
|
||
connected to either of the two cartridge slots.
|
||
|
||
Memory | PSLOT=0 | PSLOT=1 | PSLOT=2 | PSLOT=3 |
|
||
Address | MainROM | Cart. A | Cart. B | MainRAM |
|
||
-----------+---------+---------+---------+----------+
|
||
0000..3FFF | BIOS | <aux> | <aux> | RAM3 (*) |
|
||
4000..7FFF | BASIC | <aux> | <aux> | RAM2 (*) |
|
||
8000..BFFF | N/A | <aux> | <aux> | RAM1 (*) |
|
||
C000..FFFF | N/A | <aux> | <aux> | RAM0 |
|
||
|
||
(*) If less than 64K internal RAM is installed, then RAM is located in the
|
||
higher memory area only, ie. at address E000-FFFF for 8K, C000-FFFF for 16K,
|
||
etc.
|
||
|
||
Memory Map example for a MSX2 machine with built-in Disk Drive
|
||
A typical MSX2 model includes 48K ROM (called BIOS, BASIC, and SUB), and in
|
||
this example, 16K ROM for the DISK Drive. Typically 128K, 256K, or 512K RAM
|
||
are built-in.
|
||
|
||
Memory | PSLOT=0 | PSLOT=1 | PSLOT=2 | [...........PSLOT=3...........] |
|
||
Address | MainROM | Cart. A | Cart. B | SSLOT=0 SSLOT=1 SSLOT=2 SSLOT=3 |
|
||
-----------+---------+---------+---------+---------------------------------+
|
||
0000..3FFF | BIOS | <aux> | <aux> | N/A SUB RAM[3] N/A |
|
||
4000..7FFF | BASIC | <aux> | <aux> | N/A DISK RAM[2] N/A |
|
||
8000..BFFF | N/A | <aux> | <aux> | N/A N/A RAM[1] N/A |
|
||
C000..FFFF | N/A | <aux> | <aux> | N/A N/A RAM[0] N/A |
|
||
|
||
Because of the additional internal ROM, Slot 3 is sub-classed into 4 slots by
|
||
using a new Secondary Slot Register (Memory FFFFh, see below). The RAM is
|
||
split into 16K banks, four of these banks can be mapped into memory at once by
|
||
using a Memory Mapper (Port FCh-FFh, see below).
|
||
|
||
Port 0A8h, Primary Slot Register (PSLOT, PPI Port A) (Read/Write)
|
||
Used to select internal RAM, or ROM, or external memory (cartridges) into CPU
|
||
address space, as shown in the examples above. In some cases also used to
|
||
select 'memory mapped I/O ports' into memory.
|
||
Bit Expl.
|
||
0-1 PSLOT number 0-3 for memory at 0000-3FFF
|
||
2-3 PSLOT number 0-3 for memory at 4000-7FFF
|
||
4-5 PSLOT number 0-3 for memory at 8000-BFFF
|
||
6-7 PSLOT number 0-3 for memory at C000-FFFF
|
||
The PSLOT register is available in all MSX models, and Slot 0 is always used
|
||
for Main ROM. However, there is no standard for the assignment of Slot 1-3.
|
||
For example, RAM might be located in Slot 1, or Slot 2, or Slot 3.
|
||
|
||
Memory PSLOT:FFFFh, Secondary Slot Register (SSLOT) (Read Inverted, Write)
|
||
Used to subclass a Primary Slot into four Secondary Slots. Before accessing a
|
||
secondary slot register its primary slot must be selected into memory at
|
||
C000-FFFF (done by Bit 6-7 of Port A8h). The new SSLOT value may then be
|
||
written to memory address FFFFh, reading from that address returns the current
|
||
SSLOT value XORed by FFh (this behaviour might be used to detect the presence
|
||
of a secondary slot).
|
||
Bit Expl.
|
||
0-1 SSLOT number 0-3 for memory at 0000-3FFF of respective PSLOT
|
||
2-3 SSLOT number 0-3 for memory at 4000-7FFF of respective PSLOT
|
||
4-5 SSLOT number 0-3 for memory at 8000-BFFF of respective PSLOT
|
||
6-7 SSLOT number 0-3 for memory at C000-FFFF of respective PSLOT
|
||
Theoretically each PSLOT could be subclassed by separate SSLOT registers.
|
||
Commonly only one of the PSLOTs is subclassed though, and older computers with
|
||
not more than 32K ROM do not contain any SSLOT registers at all. Beside for
|
||
the internal usuage, SSLOTs might be found in Slot Expansion Cartridges which
|
||
would then allow to connect up to four cartridges to a single cartride slot.
|
||
As for PSLOTs, there is no standard that defines which PSLOT should contain an
|
||
SSLOTs, and which of the SSLOTs should contain RAM...
|
||
|
||
Memory Mapper (RAM Banking)
|
||
A memory mapper is usually available in MSX computers with more than 64K
|
||
internal RAM. The BIOS initializes these banks in reversed order, ie. the
|
||
default values for Port FC-FF are 03-00.
|
||
Port FC RAM bank number to be mapped at 0000-3FFF
|
||
Port FD RAM bank number to be mapped at 4000-7FFF
|
||
Port FE RAM bank number to be mapped at 8000-BFFF
|
||
Port FF RAM bank number to be mapped at C000-FFFF
|
||
Usually the mapping circuit latches only the actually used lower 3, 4, or 5
|
||
bits of the bank numbers, depending on whether 128K, 256K, or 512K RAM are
|
||
built-in. Theoretically (fully exanped) a total of 4MByte RAM (16Kbyte * 256
|
||
blocks) could be controlled by the mapping registers.
|
||
To enable/disable RAM, use the PSLOT register (Port A8h), and (if any) the
|
||
SSLOT register (Address FFFFh).
|
||
|
||
Memory Mapped I/O
|
||
Beside for RAM and ROM some of the addresses of some slots might be also used
|
||
as memory mapped I/O Ports. (For example for Disk Controllers, and Cartridge
|
||
Memory Mappers, and the Secondary Slot register.)
|
||
|
||
Cartridge Memory Mappers
|
||
Cartridges with more than 64K ROM or RAM must include their own memory mappers
|
||
(cartridges with 64K ROM often include a mapper also, even though it isn't
|
||
actually required). Various different mappers exist, read the chapter about
|
||
Cartridge Memory Mappers for more information about the must commonly used
|
||
chips.
|
||
|
||
Further Memory
|
||
Video Memory is not part of the memory map because VRAM can be accessed
|
||
through I/O ports only (as described in the chapter about the Video Display
|
||
Processor). Some computers may also include japanese character set ROMs, these
|
||
can be read out only through I/O ports either (as described in the chapter
|
||
about Kanji ROM).
|
||
|
||
Peripheral Interface
|
||
--------------------
|
||
|
||
8255A/ULA9RA041 PPI (Programmable Peripheral Interface)
|
||
|
||
Port A8 PPI Port A Memory PSLOT Register (RAM/ROM) (Read/Write)
|
||
Port A9 PPI Port B Keyboard column inputs (Used as Read Only)
|
||
Port AA PPI Port C Kbd Row sel,LED,CASo,CASm (Read/Write)
|
||
Port AB PPI Mode select and I/O setup of A,B,C (Write Only)
|
||
|
||
Port 0A8h, PPI Port A - Primary Slot Register (PSLOT) (Read/Write)
|
||
Bit Expl.
|
||
0-1 PSLOT number 0-3 for memory at 0000-3FFF
|
||
2-3 PSLOT number 0-3 for memory at 4000-7FFF
|
||
4-5 PSLOT number 0-3 for memory at 8000-BFFF
|
||
6-7 PSLOT number 0-3 for memory at C000-FFFF
|
||
Used to select internal RAM, or ROM, or external memory (cartridges) into CPU
|
||
address space, for more info read the chapter about Memory.
|
||
In some cases also used to select 'memory mapped I/O ports' into memory.
|
||
|
||
Port 0A9h, PPI Port B - Keyboard Column Inputs (Read Only)
|
||
Reading this port will get back the state of the selected keyboard line
|
||
(selected via port 0AAh).
|
||
Bit Name Expl.
|
||
0-7 KC0-7 Keyboard line status
|
||
Each bit corresponds to one of 8 keys on each line, as shown in the 'Keyboard
|
||
Matrix' (see below).
|
||
|
||
Port 0AAh, PPI Port C - Keyboard Row,LED,Cassette (Read/Write)
|
||
Bit Name Expl.
|
||
0-3 KB0-3 Keyboard line (0-8 on SV738 X'Press)
|
||
4 CASON Cassette motor relay (0=On, 1=Off)
|
||
5 CASW Cassette audio out (Pulse)
|
||
6 CAPS CAPS-LOCK lamp (0=On, 1=Off)
|
||
7 SOUND Keyboard klick bit (Pulse)
|
||
To generate a 50Hz sound, turn bit7 on and off at a rate of 50Hz.
|
||
For Keyboard input, see PPI Port B. For Keyboard Matrix, see below.
|
||
For Joystick input/output, and for Cassette input, see PSG Sound Generator.
|
||
|
||
Port 0ABh, PPI Control Register (Write Only)
|
||
This port is used in two ways depending on bit 7. If bit7 is zero, then this
|
||
port can be used to set or reset a single bit in PPI register C. This is just
|
||
an alternate method to modify bits in register C than by writing to it
|
||
directly (via Port AAh).
|
||
Bit Name Expl.
|
||
0 B Set/reset the bit (0=Reset, 1=Set)
|
||
1-3 N0-N2 Bit number (0-7)
|
||
4-6 0 Not used
|
||
7 SF Must be "0" for bit set/reset function.
|
||
Otherwise, if bit7 is set, then this port is used as Mode Setup for PPI Port
|
||
A-C. Theoretically these registers can be used as input or output ports.
|
||
However, in the MSX, PPI Port A and C are always used as output, and PPI Port
|
||
B as input. The BIOS initializes it like that by writing 82h to Port ABh on
|
||
startup. Afterwards it makes no sense to change this setting, and thus needs
|
||
no further explanatation here.
|
||
|
||
The MSX Keyboard Matrix
|
||
The names in this table refer to the original MSX1 keyboard map (which is
|
||
mostly identical to the US-keymap on PCs).
|
||
Line Bit_7 Bit_6 Bit_5 Bit_4 Bit_3 Bit_2 Bit_1 Bit_0
|
||
0 "7" "6" "5" "4" "3" "2" "1" "0"
|
||
1 ";" "]" "[" "\" "=" "-" "9" "8"
|
||
2 "B" "A" ??? "/" "." "," "'" "`"
|
||
3 "J" "I" "H" "G" "F" "E" "D" "C"
|
||
4 "R" "Q" "P" "O" "N" "M" "L" "K"
|
||
5 "Z" "Y" "X" "W" "V" "U" "T" "S"
|
||
6 F3 F2 F1 CODE CAP GRAPH CTRL SHIFT
|
||
7 RET SEL BS STOP TAB ESC F5 F4
|
||
8 RIGHT DOWN UP LEFT DEL INS HOME SPACE
|
||
( 9 NUM4 NUM3 NUM2 NUM1 NUM0 NUM/ NUM+ NUM* )
|
||
( 10 NUM. NUM, NUM- NUM9 NUM8 NUM7 NUM6 NUM5 )
|
||
Line 9 and 10 are used/reserved for numeric keypad, the NUM/, NUM+, NUM* keys
|
||
might be exchanged in some coutries. (Most MSX1 and MSX2 models do not include
|
||
a numeric keypad at all though).
|
||
|
||
MSX2 models have been delivered with country-specific BIOSes and keymaps, in
|
||
that case the logical keynames change. For example the key in Line 1, Bit 5 is
|
||
always the key to the right of the "P"-key, but on german keyboards that key
|
||
would be used as "UE" rather than "[".
|
||
|
||
About the five function keys (F1-F5), note that the key-combinations
|
||
Shift+F1-F5 are often referred to as F6-F10 in the MSX world. The GRAPH key
|
||
would be the LEFT ALT key on a PC keyboard, CODE would be RIGHT ALT, and
|
||
SELECT and STOP could be mapped as PAGE-UP/DN and END.
|
||
|
||
Video Display Processor
|
||
-----------------------
|
||
|
||
--> VDP I/O Ports
|
||
--> Video Modes (Screens)
|
||
--> Foreground Sprites
|
||
--> VRAM Data Read/Write
|
||
--> VDP Status Registers
|
||
--> VDP Register Write
|
||
--> VDP Registers 00h-07h: Basic MSX1/MSX2 Video Registers
|
||
--> VDP Registers 08h-17h: Additional MSX2 Video Registers
|
||
--> VDP Registers 18h-1Fh: MSX2+/turbo R Video Registers
|
||
--> VDP Registers 20h-2Eh: MSX2 Video Command Registers
|
||
--> Display Timings
|
||
--> VDP Interrupts
|
||
|
||
VDP I/O Ports
|
||
-------------
|
||
|
||
Port 98-99 Internal VDP (V9918 for MSX1)
|
||
Port 98-9B Internal VDP (V9938 for MSX2, V9958 for MSX2+/turbo R)
|
||
Port 88-8B External VDP (V9938 upgrade for MSX1)
|
||
|
||
Internal VDP
|
||
Port 98 VRAM Data (Read/Write)
|
||
Port 99 VDP Status Registers (Read Only)
|
||
Port 99 2nd Byte b7=0: VRAM Address setup (Write Only)
|
||
Port 99 2nd Byte b7=1: VDP Register write (Write Only)
|
||
Port 9A MSX2 Only: Palette Register (2 bytes) (Write Only)
|
||
Port 9B MSX2 Only: Register Data (Write Only)
|
||
|
||
External VDP 9938
|
||
MSX1 computers could be upgraded to MSX2 by a special cartridge which includes
|
||
a V9938 display processor and MSX2 BIOS ROMs. The V9938 is accessed through
|
||
Port 88h-8Bh (in same way as Port 98h-9Bh of internal VDP). A programmer
|
||
should always verify bytes at address 0006h and 0007h in Main-ROM which
|
||
specify the VDP Port address.
|
||
|
||
Video Modes (Screens)
|
||
---------------------
|
||
|
||
This chapter describes the standard VRAM map for the different MSX video modes
|
||
(screens). Note that these default addresses can be changed by modifying VDP
|
||
registers 2-6.
|
||
|
||
The VDP Video Modes (BASIC Screen 0-8) is selected by the Bits M1-M5 of VDP
|
||
Register 0 and 1. The relationship between the bits and the screen is:
|
||
M1 M2 M3 M4 M5 Screen format
|
||
1 0 0 0 0 Text 40x24 (BASIC SCREEN 0)
|
||
0 0 0 0 0 Half text 32x24 (BASIC SCREEN 1)
|
||
0 0 1 0 0 Hi resolution 256x192 (BASIC SCREEN 2)
|
||
0 1 0 0 0 Multicolour 4x4pix blocks (BASIC SCREEN 3)
|
||
----Below MSX2 only----
|
||
0 0 0 1 0 Screen2 with 8 Sprites/Line (BASIC SCREEN 4)
|
||
0 0 1 1 0 256*212, 16 colours/pixel (BASIC SCREEN 5)
|
||
0 0 0 0 1 512*212, 4 colours/pixel (BASIC SCREEN 6)
|
||
0 0 1 0 1 512*212, 16 colours/pixel (BASIC SCREEN 7)
|
||
0 0 1 1 1 256*212, 256 colours/pixel (BASIC SCREEN 8)
|
||
1 0 0 1 0 Text 80x24 (BASIC SCREEN 0, WIDTH 80)
|
||
The above vertical default resolutions could be changed by modifying bit 7 of
|
||
VDP register 9.
|
||
|
||
Screen 0-3 are available on both MSX1 and MSX2, the other screens are
|
||
supported on MSX2 only.
|
||
|
||
SCREEN 0 - 40x24 text mode
|
||
0000-03BF BG Map
|
||
0800-0FFF BG Tiles
|
||
In screen 0, the tiles are defined as usually (8x8 pixels), but only the
|
||
leftmost 6x8 pixels of each tile are visible.
|
||
|
||
SCREEN 1 - 32x24 coloured text mode
|
||
0000-07FF BG Tiles
|
||
1800-1AFF BG Map
|
||
1B00-1B7F OBJ Attributes
|
||
2000-201F BG Colors
|
||
3800-3FFF OBJ Tiles
|
||
The BG Colors array defines 32 colors (each 4 bit background, and 4 bit
|
||
foreground, as in VDP register 7). The colors are assigned to the BG Tiles as
|
||
follows: Tiles 00..07 share the first color, tiles 08..0F share the second
|
||
color, etc, and tiles F8..FF share the last color.
|
||
|
||
SCREEN 2 - 256*192 Graphics mode
|
||
0000-17FF BG Tiles
|
||
1800-1AFF BG Map
|
||
1B00-1B7F OBJ Attributes
|
||
2000-37FF BG Colors
|
||
3800-3FFF OBJ Tiles
|
||
The BG Tiles array can be placed only at address 0000h or 2000h, ie. only bit
|
||
2 of VDP Register 4 is used. The BG Colors array is placed at the same address
|
||
XORed by 2000h (ie. either at 2000h or 0000h).
|
||
|
||
In screen 2, the BG Tile memory consists of 300h tiles. The screen is
|
||
vertically divided into 3 sections, all BG Map entries for the upper 8
|
||
character rows refer to tiles 00..FFh, the middle 8 rows to tiles 100..1FFh,
|
||
and the bottom 8 rows to tiles 200..2FFh.
|
||
|
||
As usually, all TILE-BYTES define rows of eight pixels, each of these rows is
|
||
colorized by a separate COLOR-BYTE in the BG Colors array, whereas each
|
||
COLOR-BYTE defines the background color in bit 0-3 (for "0" bits in TILE-BYTE)
|
||
and the foreground color in bit 4-7 (for "1" bits). That means there can be
|
||
only 2 different colors in each row of 8 pixels!
|
||
|
||
SCREEN 3 (64*48 block graphics multicolour mode)
|
||
0000-07FF BG Tiles (block colors)
|
||
0800-0AFF BG Map
|
||
1B00-1B7F Sprite attribute table
|
||
3800-3FFF Sprite character patterns
|
||
The screen consists of 32x24 background tiles, each tile consists of 4 blocks,
|
||
whereas each of these "pixels" can be colorized in any of the available 16
|
||
colors.
|
||
|
||
The BG Tile memory is organized as follows: It contains 8 color bytes for each
|
||
of the 100h tiles. But obviously only two bytes are actually required (first
|
||
byte for the upper half, and second byte for the lower half, in both cases
|
||
most significant bits for the left 'pixels').
|
||
|
||
Which of the 8 bytes are used depends on the lower two bits of the vertical
|
||
position (0-23), ie. tiles in lines 0,4,8,12,etc. use the first two bytes,
|
||
tiles in lines 1,5,9,etc. use the next two bytes, and so on.
|
||
|
||
--- Below Screens 4-8 and the 80 column text screen exist on MSX2 only ---
|
||
|
||
SCREEN 4 (256*192 Graphics mode with multicolour sprites):
|
||
0000-17FF Charcter patterns
|
||
1800-1AFF Name table (char positions)
|
||
1C00-1DFF Sprite colours
|
||
1E00-1E7F Sprite attribute table
|
||
1E80-1E9F Palette
|
||
2000-37FF PixelByte colour table
|
||
3800-3FFF Sprite character patterns
|
||
This is mostly the same as Screen 2, except that the foregound sprites can
|
||
have additional color attributes, and with the abilty to display a maximum of
|
||
8 sprites per line.
|
||
|
||
The "Palette" entry in the memory maps for screen 4-8 does not have a physical
|
||
function. It is just a memory location where the MSX BIOS usually places a
|
||
copy of the actual VDP palettes. For more information read the BASIC manual
|
||
about the COLOR=RESTORE function.
|
||
|
||
SCREEN 5 (256*212 Graphic mode, 16 colours):
|
||
0000-69FF Matrix (Bitmap)
|
||
7400-75FF Sprite colours
|
||
7600-767F Sprite attribute table
|
||
7680-769F Palette
|
||
7800-7FFF Sprite character patterns
|
||
|
||
SCREEN 6 (512*212 Graphic mode, 4 colours):
|
||
0000-69FF Matrix (Bitmap)
|
||
7400-75FF Sprite colours
|
||
7600-767F Sprite attribute table
|
||
7680-769F Palette
|
||
7800-7FFF Sprite character patterns
|
||
|
||
SCREEN 7 (512*212 Graphic mode, 16 colours):
|
||
0000-D3FF Matrix (Bitmap)
|
||
F000-F7FF Sprite character patterns
|
||
F800-F9FF Sprite colours
|
||
FA00-FA7F Sprite attribute table
|
||
FA80-FA9F Palette
|
||
No$hackwork: (Even/Odd VRAM addressing)
|
||
In screen 7 and 8 (the video modes with 256 bytes per line), the video RAM is
|
||
addressed differently as usually.
|
||
|
||
In these modes, the first 64K VRAM are used for even addresses, and the second
|
||
64K for ODD addresses. Ie. the address lines aren't A16..A0, rather it is
|
||
A15..A0,A16. That method allows the video controller to increment the lower
|
||
address lines at the same clock rate as in 128 byte/line modes.
|
||
|
||
The funny thing about that is, that it isn't visible for the programmer, ie.
|
||
to set the 6th dot in first line in screen 8, (or the 12th and 13th, in screen
|
||
7), the program would still have to write to the (virtual) address 00005h, as
|
||
if there would be no special even/odd feature. But physically the byte would
|
||
be written to address 10002h!
|
||
|
||
As noted above, that is all done behind your back, and you don't have to care
|
||
about it at all - EXCEPT if you write data into VRAM before you set up the
|
||
desired video mode, ie. if you switch to screen 7/8 (or back), then any data
|
||
that is already in VRAM changes it's position! Virtually at least...
|
||
|
||
SCREEN 8 (256*212 Graphic mode, 256 colours):
|
||
0000-D3FF RGB Matrix (Bitmap)
|
||
F000-F7FF Sprite character patterns
|
||
F800-F9FF Sprite colours (See note I)
|
||
FA00-FA7F Sprite attribute table
|
||
FA80-FA9F Palette (Huh?)
|
||
Each byte in the RGB Matrix defines a separate pixel. The bytes directly
|
||
define the colors as follows:
|
||
Bit 0-1 Blue, 0-3
|
||
Bit 2-4 Red, 0-7
|
||
Bit 5-7 Green, 0-7
|
||
Also read the description about even/odd VRAM addressing in screen 7 and 8.
|
||
(See screen 7 description above.)
|
||
|
||
SCREEN 0 (Text mode, 80 column):
|
||
0000-077F (086F) Name table (char positions)
|
||
0800-08EF (090D) Character attribute (Blink)
|
||
1000-17FF Character patterns (font)
|
||
(Addresses in pharentheses is used in 26.5 lines mode. Observe that they are
|
||
overlapping).
|
||
The Characters attribute table is an array of bits, ie. the first byte of the
|
||
table contains bits for the first 8 characters on the screen.
|
||
|
||
If the attribute-bit is zero, then the character is displayed as usually
|
||
(colored as defined in VDP Reg 07h). If the bit is set, then the character is
|
||
blinking (see VDP Reg 0Ch, and VDP Reg 0Dh).
|
||
|
||
Foreground Sprites
|
||
------------------
|
||
|
||
OBJ Attributes (Sprite attribute):
|
||
Defines 'OAM' data for up to 32 foreground sprites. Each entry consists of
|
||
four bytes:
|
||
0: Y-pos, Vertical position (FFh is topmost, 00h is second line, etc.)
|
||
1: X-pos, Horizontal position (00h is leftmost)
|
||
2: Pattern number
|
||
3: Attributes. b0-3:Color, b4-6:unused, b7:EC (Early Clock)
|
||
If EC is set to 1, the X-pos is subtracted by 32 (can be used to place sprites
|
||
particulary offscreen to the left.
|
||
|
||
When using 16x16 pixel sprites the lower two bits of the sprite number are
|
||
ignored (should be zero). A 16x16 sprite logically consists of four 8x8
|
||
sprites, whereas the first 8x8 sprite is displayed in upperleft, the second
|
||
one in lower left, the third in upper right, and the fourth in lower right.
|
||
|
||
If Y-pos is set to 208 (D0h), the sprite AND ALL FOLLOWING sprites are hidden!
|
||
For MSX2 video modes (Screen 4-8), the same happens if Y-pos is set to 216
|
||
(D8h).
|
||
|
||
If the display is scrolled via VDP register 17h, this also affects the
|
||
positions of the sprites! Ie. the actual visible position of the sprite would
|
||
be YLOC+1-VDP(17h).
|
||
However, the special hide-the-sprites-value (YLOC=216) is hardcoded,
|
||
independendly of the screen offset in VDP register 17h! If a sprite should be
|
||
displayed in that line, either 215 or 217 must be used instead!
|
||
|
||
Sprite colours
|
||
In MSX2 video modes with colored sprites (screen 4-8), the fourth byte of the
|
||
OAM entires is unused. Instead, the sprite attributes are stored in a separate
|
||
'color table'.
|
||
That table is always placed at the address of the above sprite attribute table
|
||
minus 200h. The color table contains 20h entries (one for each entry of the
|
||
OAM table), and each entry is sized 10h bytes.
|
||
The 10h bytes of each entry specify color & attributes for each line of the
|
||
displayed sprites (assuming that the sprite size is set to 16x16).
|
||
|
||
The bytes in that color table are used as follow:
|
||
Bit 0-3 CL Color Code (0-15)
|
||
Bit 4 0 Unused
|
||
Bit 5 IC Ignore collisions with other sprites. (1=Ignore)
|
||
Bit 6 CC Mix color with sprite that has next higher priority.
|
||
Bit 7 EC Early clock (shift this line of the sprite 32 pixels to left)
|
||
For screen 4-7 the color code specifies the desired palette color, for screen
|
||
8 the sprite colors are hardcoded as follows:
|
||
Bit 0 Blue (1=on, 0=off)
|
||
Bit 1 Red (1=on, 0=off)
|
||
Bit 2 Green (1=on, 0=off)
|
||
Bit 3 Intensity (1=Light, 0=dark)
|
||
If the intensity-bit is set alone (with b0-2 cleared, ie. color 8), then
|
||
something like bright pink or bright orange is displayed instead.
|
||
|
||
When CC is set, the color of the sprite is logically ORed with the pixels of
|
||
the sprite "that has the next higher priority, and that has CC=0". In that
|
||
case a collision just mixes colors, and does not causes a conflict, ie. bit 5
|
||
of status register 0 doesn't get set.
|
||
|
||
If a line of a sprite has the CC bit set, then it MUST collide with at least
|
||
one pixel of another sprite with higher priority, otherwise the line of the
|
||
sprite isn't displayed at all!
|
||
|
||
VRAM Data Read/Write
|
||
--------------------
|
||
|
||
Port 98 VRAM Data (Read/Write)
|
||
Port 99 VRAM Address setup (2nd Byte b7=0) (Write Only)
|
||
|
||
Port 98h, Accessing VRAM Data
|
||
Read data from VRAM, or write data to VRAM. In either case the VRAM read/write
|
||
pointer is automatically incremented, allowing to read/write a stream of bytes
|
||
without having to setup the pointer each time.
|
||
|
||
Port 99h, VRAM Address Pointer Setup
|
||
The VRAM read/write pointer is initalized by writing TWO BYTES to port 99h
|
||
with BIT 7 CLEARED in the second byte.
|
||
Byte 1/Bit 0-7 Lower bits of VRAM Pointer
|
||
Byte 2/Bit 0-5 Upper bits of VRAM Pointer
|
||
Byte 2/Bit 6 Desired VRAM Direction (0=Reading, 1=Writing)
|
||
Byte 2/Bit 7 Must be "0" for VRAM Pointer setup
|
||
This 14bit Pointer value allows to address 16Kbytes of VRAM (ie. the complete
|
||
VRAM of MSX1 models). From what I understand, if the Direction is set up for
|
||
Reading, VRAM data becomes latched immediately, and the pointer becomes
|
||
incremented <before> data is actually read from Port 98h. If so, note that the
|
||
latched byte might contain old data if the Pointer hasn't been set up
|
||
previously.
|
||
|
||
Addressing more than 16K VRAM (MSX2 only)
|
||
On MSX2 the upper bits of the above 14bit pointer can be specified in VDP
|
||
Register 0Eh, allowing to address the total of 128K VRAM. This register
|
||
becomes automatically incremented when the 14bit read/write pointer overflows,
|
||
for MSX1 compatibility this happens only in MSX2 video modes though.
|
||
Additional 64K VRAM (if any) can be addressed by setting MXC bit of VDP
|
||
Register 2Dh.
|
||
|
||
VDP Status Registers
|
||
--------------------
|
||
|
||
Port 99 VDP Status Registers (Read Only)
|
||
|
||
MSX1 includes only one VDP Status Register (Register 0), for MSX2 VDP Status
|
||
Registers 0-9 exist.
|
||
|
||
Status register 0 (default):
|
||
Bit Name Expl.
|
||
0-4 5/9th Number for the 5th sprite (9th in screen 4-8) on a line
|
||
5 C 1 if overlapping sprites
|
||
6 5D 1 if more than 4 sprites on a horizontal line (8 in screen 4-8)
|
||
7 F V-Blank IRQ Flag (1=interrupt) (See also IE0 flag)
|
||
In screen 1-3 only 4 sprites can be displayed per line, in screen 4-8 this
|
||
number is doubled to 8 sprites per line. Bit 6 indicates if too many sprites
|
||
have been (attempted to be) displayed. If the bit is set, Bit 0-4 indicate the
|
||
number of the sprite that wasn't displayed properly. If more than one sprite
|
||
haven't displayed properly, then Bit 0-4 specify the first of these bad
|
||
sprites.
|
||
|
||
A sprite is overlapping another if a non-transparent pixel of a sprite hits a
|
||
non-transparent pixel of another sprite. Whereas in MSX2 colored sprite modes
|
||
this verfication can be made optional for specific sprites by CC and IC bits
|
||
in the sprite OAM data.
|
||
|
||
The IRQ flag in bit 7 gets set at the beginning of the VBlank period, if IE0
|
||
in VDP Register 1 is set (or gets set at a later time, while the IRQ flag is
|
||
still set) then an interrupt is generated.
|
||
|
||
The IRQ flag (bit 7) and the collision flag (bit 5) get cleared after reading
|
||
Status register 0.
|
||
BUG: When reading this register at the same time when IRQ changes from 0 to 1,
|
||
this sometimes results in old value to be read (IRQ=0) before it becomes
|
||
changed to 1, but the read-signal still acknowledges the IRQ (and sets it back
|
||
to IRQ=0) - in that case the IRQ is lost.
|
||
|
||
Below Status Registers 1-9 exist on MSX2 only
|
||
|
||
To access these registers, first set the Status Register Index in VDP Register
|
||
0Fh, then read from port 99h, for compatibility to BIOS functions and MSX1
|
||
software the index should be always restored to zero after usage.
|
||
|
||
Status register 1: Interrupt Status
|
||
Bit Name Expl.
|
||
0 FH Horizontal Retrace IRQ Flag (See also: VDP Reg 13h and IE1 flag)
|
||
1-5 ID# VDP Type (0=V9938/MSX2, 2=V9958/MSX2+ and Turbo R, 1=V9948?!)
|
||
6 LPS Light Pen ??? (MSX2 only, Not MSX2+)
|
||
7 FL Light Pen and/or Mouse ??? (MSX2 only, Not MSX2+)
|
||
|
||
Status register 2: VDP Command Status
|
||
Bit Name Expl.
|
||
0 CE Command Execute (0=Finished, 1=VDP Command still
|
||
executing)
|
||
1 EO Display field flag (??) (0=display first field)
|
||
2-3 0 Not Used
|
||
4 BO Search Command Result (0=Not found, 1=Found)
|
||
5 HR Horizontal Retrace Flag (1=HBlank)
|
||
6 VR Vertical Retrace Flag (1=VBlank)
|
||
7 TR Data Ready (For CPU <--> VRAM Commands) (0=Not Ready, 1=Ready)
|
||
Despite of its name, the Vertical Retrace Flag is set for the entire time
|
||
while lower and upper screen borders are drawn and during actual vertical
|
||
retrace. The Horizontal Retrace Flag becomes set at the end of each scanline -
|
||
including hidden/dummy scanlines during vertical retrace.
|
||
|
||
Status register 3: X-Coordinate+12 of sprite conflict (low)
|
||
Status register 4: X-Coordinate+12 of sprite conflict (high)
|
||
Status register 5: Y-Coordinate+8 of sprite conflict (low)
|
||
Status register 6: Y-Coordinate+8 of sprite conflict (high)
|
||
According to V9958.TXT above X/Y also used for mouse/lightpen (?)
|
||
|
||
Status register 7: Result from VRAM -> VDP/CPU Commands
|
||
Bit 0-7 Color Code
|
||
|
||
Status register 8: Result of Search Command, X-Loc (low)
|
||
Status register 9: Result of Search Command, X-Loc (high)
|
||
|
||
VDP Register Write
|
||
------------------
|
||
|
||
Port 99 VDP Register Setup (2nd Byte b7=1) (Write Only)
|
||
Port 9A VDP Palette Register (MSX2 only) (2 bytes, Write Only)
|
||
Port 9B VDP Register Data (MSX2 only) (Write Only)
|
||
|
||
Port 99h, VDP Register Setup (Data, Index)
|
||
A VDP Register can be changed by writing TWO BYTES to port 99h with BIT 7 SET
|
||
in the second byte.
|
||
Byte 1, Bit 0-7 Data (New value for the register)
|
||
Byte 2, Bit 0-6 Index (VDP register number) (MSX1: 0-7, MSX2: 0-2E)
|
||
Byte 2, Bit 7 Must be "1" for VDP Register setup
|
||
|
||
Port 9Ah, MVDP MSX2 Color Palette Register
|
||
Before writing to this port, select a the Color Number (0-15) by writing to
|
||
VDP register 10h. Then output the RGB data for the selected color to Port
|
||
09Ah. The RGB data consists of two bytes:
|
||
Byte 1, Bit 0-2 Blue data (0-7)
|
||
Byte 1, Bit 4-6 Red data (0-7)
|
||
Byte 2, Bit 0-2 Green data (0-7)
|
||
Byte 1, Bit 3,7 Always 0 (no effect)
|
||
Byte 2, Bit 3-7 Always 0 (no effect)
|
||
Note: The index in VDP register 10h becomes automatically incremented after
|
||
the second byte has been written.
|
||
|
||
Port 9Bh, VDP Register Data (Raw Data, Write only)
|
||
This register offers an alternate method to access the VDP registers on MSX2
|
||
computers. (Normally VDP registers are set by writing TWO bytes (data, index)
|
||
to Port 99h as described above).
|
||
|
||
Writing to port 9Bh directly sets the VDP register that is addressed by VDP
|
||
Register 11h. Afterwards (if the auto increment bit was set) the value in
|
||
register 11h gets incremented automatically. (See VDP register 11h description
|
||
for more details).
|
||
|
||
Example for Port 9Bh: Initializing VDP registers 00h..17h
|
||
Write 00h (index 00h, increment=on) to VDP register 11h (using the oldstyle
|
||
method through port 99h). Now write 18h bytes of data for registers 00h..17h
|
||
to 9Bh (The data written to Register 11h is ignored, so that it can't damage
|
||
itself).
|
||
|
||
VDP Registers 00h-07h: Basic MSX1/MSX2 Video Registers
|
||
------------------------------------------------------
|
||
|
||
The VDP register can be (on MSX 1) in the range of 0-7.
|
||
On the MSX2 VDP (the one in the SV738 X'Press) it can be in the range of
|
||
0-2Eh.
|
||
|
||
Register 0: Mode register 0
|
||
Bit Name Expl.
|
||
0 D External video input (0=input disable, 1=enable)
|
||
1 M3 Mode M3 (Screen 2,5,7,8)
|
||
2 M4 Mode M4 (Screen 4,5,8,0Hi) (MSX2 only)
|
||
3 M5 Mode M5 (Screen 6,7,8) (MSX2 only)
|
||
4 IE1 H-Blank Interrupt Enable (MSX2 only) (see also VDP Reg 13h)
|
||
5 IE2 Light pen/mouse on ??? (MSX2 ONLY not MSX2+)
|
||
6 DG DiGitize mode (MSX2 only)
|
||
7 0 Not Used
|
||
|
||
Register 1: Mode register 1
|
||
Bit Name Expl.
|
||
0 MAG Sprite zoom (0=x1, 1=x2)
|
||
1 SZ Sprite size (0=8x8, 1=16x16)
|
||
2 0 Not Used
|
||
3 M2 Mode M2 (Screen 3: Block)
|
||
4 M1 Mode M1 (Screen 0: Text)
|
||
5 IE0 V-Blank Interrupt Enable (0=Disable, 1=Enable)
|
||
6 BLK Screen output control (0=Disable, 1=Enable)
|
||
7 416 VRAM size control (0=4K, 1=16K) (No Function on MSX)
|
||
|
||
Register 2: BG Map (Name table) base address
|
||
Bit 7 6 5 4 3 2 1 0
|
||
Name 0 A16 A15 A14 A13 A12 A11 A10
|
||
In screen 0-4 this register specifies the base address of the background map
|
||
(that refers to the tiles that should be displayed as background). In screen
|
||
5-8 the register points to the base address of the background bitmap, whereas
|
||
in screen 5 and 6 only A16 and A15 are used.
|
||
In screen 7 and 8 only Bit 5 of the register is used, in these two screens
|
||
VRAM is physically separated into two 64K blocks for even/odd addresses, so
|
||
A15 is the most significant bit, for more info read the details in screen 7
|
||
description.
|
||
|
||
Register 3: BG Colors (Colour table) base address Low
|
||
Bit 7 6 5 4 3 2 1 0
|
||
Name A13 A12 A11 A10 A09 A08 A07 A06
|
||
In screen 2 and 4 the bits for A12-A06 are ignored, making the address a
|
||
multiple of 2000h. The register isn't used in screen 5-8, and screen 0/width
|
||
40. In screen 0/width 80 the bits for A06-A10 are ignored, making the address
|
||
a multiple of 800h.
|
||
|
||
Register 4: BG Tiles (Pattern generator) base address
|
||
Bit 7 6 5 4 3 2 1 0
|
||
Name 0 0 A16 A15 A14 A13 A12 A11
|
||
In screen 2 and 4 the bits for A12 and A11 are ignored, making the address a
|
||
multiple of 2000h. The register isn't used in screen 5-8.
|
||
|
||
Register 5: OBJ Attr (Sprite attribute table) base address Low
|
||
Bit 7 6 5 4 3 2 1 0
|
||
Name A14 A13 A12 A11 A10 A09 A08 A07
|
||
In screen 4-8 (colored sprite mode) the bits for A8 and A7 ignored, making the
|
||
address a multiple of 200h, in these video modes the register additionally
|
||
specifies the address of the 'sprite color table' which is always placed 200h
|
||
bytes before the sprite attribute table. Not used in screen 0.
|
||
|
||
Register 6: OBJ Tiles (Sprite pattern generator) base address
|
||
Bit 7 6 5 4 3 2 1 0
|
||
Name 0 0 A16 A15 A14 A13 A12 A11
|
||
Not used in screen 0.
|
||
|
||
Register 7: colour register.
|
||
Bit Name Expl.
|
||
0-3 TC0-3 Background colour in SCREEN 0 (also border colour in SCREEN 1-3)
|
||
4-7 BD0-3 Foreground colour in SCREEN 0
|
||
The bits 0-3 and 4-7 can hold a number in the range of 0-15.
|
||
The corresponding colours are:
|
||
0 = Transparent 8 = Medium red
|
||
1 = Black 9 = Light red
|
||
2 = Medium green 10= Dark yellow
|
||
3 = Light green 11= Light yellow
|
||
4 = Dark blue 12= Dark green
|
||
5 = Light blue 13= Magenta
|
||
6 = Dark red 14= Gray
|
||
7 = Cyan 15= White
|
||
Color 0 is transparent only if used for foreground text/sprites. But it is
|
||
visible when it is used for the background itself, whereas the color assigned
|
||
to color 0 is just black - on MSX2 the palettes for all colors (including
|
||
color 0) can be redefined though.
|
||
In Screen 8 the register contains a 8bit value that specifies the RGB values
|
||
for the screen border (in same format as for the screen 8 pixels).
|
||
In screen 6 this register is having a rather exotic function:
|
||
Bit Name Expl.
|
||
0-1 Background color A
|
||
2-3 Background color B
|
||
4 Enable Background color B (0=Use color A only, 1=use both)
|
||
If both color A & B are used, then the screen border (and any transparent
|
||
background) becomes drawn as diagonal stripes which are slowly wandering over
|
||
the screen.
|
||
|
||
VDP Registers 08h-17h: Additional MSX2 Video Registers
|
||
------------------------------------------------------
|
||
|
||
Registers below available in MSX2, MSX2+, and turbo R only.
|
||
|
||
Register 8: Mode register 2
|
||
Bit Name Expl.
|
||
0 BW 32 Greylevel MVDPmode out through CompositeVideo output.
|
||
(Normally composite video and RGB are not generated from this
|
||
output but from another on the MVDP).
|
||
1 SP Disable OBJ Sprites (0=On, 1=Disable)
|
||
2-3 VRS VRAM size and speed
|
||
(0=1*16KB,1=4*16KB,2=1*64KB,3=64KB/HighSpeed)
|
||
4 CB colour Bus direction (0=Output, 1=Input)
|
||
5 TP Transparent from palette (0=Normal, 1=Color 0 is solid)
|
||
6 LCS Lightpen Select (active 1) connected through colourbus (not
|
||
MSX2+)
|
||
7 MSE Mouse select (active 1) connected through colourbus (not
|
||
MSX2+)
|
||
|
||
Register 9: Mode register 3
|
||
Bit Name Expl.
|
||
0 DC Dot Clock Direction (0=Output, 1=Input) (V9958.TXT)
|
||
1 NT NTSC (0=NTSC/60Hz, 1=PAL/50Hz)
|
||
2 EO Even Odd Display (0=Normal, 1=Two screen)
|
||
3 IL Interlace (0=Off, 1=On)
|
||
4-5 S# Simultaneus mode (0=Intern, 1=Mix, 2=Extern/Digitize)
|
||
6 0 Always 0
|
||
7 LN Vertical heigth (pixels) (0=192, 1=212)
|
||
|
||
Register 0Ah: colour table base address High
|
||
Bit 7 6 5 4 3 2 1 0
|
||
Name 0 0 0 0 0 A16 A15 A14
|
||
|
||
Register 0Bh: Sprite attribute base address High
|
||
Bit 7 6 5 4 3 2 1 0
|
||
Name 0 0 0 0 0 0 A16 A15
|
||
|
||
Register 0Ch: Inverse/Blink text colour
|
||
Bit Name Expl.
|
||
0-3 BC0-3 Inverse/Blink text background colour
|
||
4-7 T20-3 Inverse/Blink text forground colour
|
||
The bits 0-3 and 4-7 can hold a number in the range of 0-15.
|
||
The corresponding colours are the same as for register 7.
|
||
|
||
Register 0Dh: Blinking period
|
||
Bit Name Expl.
|
||
0-3 OF0-3 Off blink time (1/5 sec)
|
||
4-7 ON0-3 On blink time (1/5 sec)
|
||
|
||
Register 0Eh: VRAM access (VRAM address select, higher address lines)
|
||
Bit 7 6 5 4 3 2 1 0
|
||
Name 0 0 0 0 0 A16 A15 A14
|
||
Defines the 16K bank for VRAM reads/writes through port 98h.
|
||
For MSX2 video modes, this register is automatically incremented when the
|
||
lower 14 bits in the VRAM read/write pointer overflow. However, for MSX1
|
||
compatibility, this does not happen in MSX1 video modes.
|
||
See also: Port 99h (with Bit7=0), and MXC bit in VDP Reg 2Dh
|
||
|
||
Register 0Fh: Status Register Index
|
||
Bit Name Expl.
|
||
0-3 S0-3 Status register number (0-9)
|
||
4-7 0 Always 0
|
||
For more information read the section about reading from port 99h.
|
||
|
||
Register 10h: Palette Index
|
||
Bit Name Expl.
|
||
0-3 C0-3 colour palette register number (0-15 for colour 0-15)
|
||
to receive data from port 09Ah
|
||
4-7 0 Always 0
|
||
|
||
Register 11h: Register pointer
|
||
This register offers an alternate method to access the VDP registers.
|
||
(Normally VDP registers are set by writing TWO bytes (data, index) to port
|
||
99h.)
|
||
Bit Name Expl.
|
||
0-5 R0-5 VDP Register Index (for writing data to Port 9Bh)
|
||
6 0 Always 0
|
||
7 AII Auto increment VDP index (0=on, 1=off)
|
||
For example, to initializing VDP registers 00h..17h, send 00h (index 00h,
|
||
increment=on) to VDP register 11h (through port 99h). Send 18h bytes data to
|
||
port 9Bh for registers 00h..17h, whereas the byte written to register 11h will
|
||
be ignored (the index can't damage itself).
|
||
|
||
Register 12h: Display adjust
|
||
Bit Name Expl.
|
||
0-3 H0-3 Horizontal adjust (0-0Fh, +-8 pixels)
|
||
4-7 V0-3 Vertical adjust (0-0Fh, +-8 pixels)
|
||
|
||
Register 13h: Interrupt line
|
||
This register selects the scanline number in which the Horizontal Retrace
|
||
Interrupt should occur. This may be a scanline that is part of the picture, or
|
||
of the lower screen border.
|
||
Bit Name Expl.
|
||
0-7 IL0-7 Interrupt line (0-255 in 50 Hz mode)
|
||
In 60Hz mode, the sum of the picture plus lower border lines is less than 256,
|
||
so that only line 0-EA (192 pix mode) or 0-F4 (212 pix mode) can be used.
|
||
Bit 4 in VDP Register 0 must be set to enable this function, and interrupts
|
||
must be acknowledged by reading from Status Register 1.
|
||
The scanline number in this register must be relative to the Display Offset
|
||
(Vertically Scrolling) in VDP Register 17h.
|
||
|
||
Register 14h: Colour burst register 1 - always set to 00h ?
|
||
Register 15h: Colour burst register 2 - always set to 3Bh ?
|
||
Register 16h: Colour burst register 3 - always set to 05h (portar: 15h) ?
|
||
|
||
Register 17h: Display offset
|
||
Bit Name Expl.
|
||
0-7 DO0-7 Display offset Y (0-255).
|
||
This register vertically scrolls the entire screen - including the foreground
|
||
sprites. The picture wraps around to line 0 when it reaches the bottom, ie. if
|
||
the offset is set to 200, then lines 200-255 are displayed (first 56 lines),
|
||
followed by line 0-155 (remaining 156 lines, for a total of 212 visible
|
||
lines).
|
||
|
||
VDP Registers 18h-1Fh: MSX2+/turbo R Video Registers
|
||
----------------------------------------------------
|
||
|
||
Register 18h-1Fh: Not used in MSX1 and MSX2
|
||
These eight registers haven't been used in MSX2 (and MSX1) models. However,
|
||
the V9958 video chip of the MSX2+ and turbo R models includes three new
|
||
registers in this previously unused area. The three new registers are all
|
||
initialized to "0" upon reset, and the V9958 will function compatibly with
|
||
V9938 in that state.
|
||
|
||
Register 19h: 9958 ONLY -- Horizontal Scroll Control
|
||
Bit Name Expl.
|
||
0 SP2 H-Scroll Screen Width (0=One page, 1=Two pages)
|
||
1 MSK H-Scroll Mask 8 Pixels (0=Normal, 1=Hide Leftmost Pixels)
|
||
2 WTE VRAM Access Waitstates (0=Normal, 1=Enable CPU Waitstate)
|
||
3 YJK YJK Mode Enable (0=Normal RGB, 1=YJK System)
|
||
4 YAE YJK Attribute Enable (0=No Attribute, 1=With Attribute)
|
||
5 VDS Pin 8 Output selection (0=Output CPUCLK, 1=Output /VDS)
|
||
6 CMD Video Command Mode (0=Normal, 1=Screen 2-4 as screen 8)
|
||
7 0 Not Used
|
||
The meaning of these new bits is relative complicated, read on below for
|
||
detailed information.
|
||
|
||
Register 1Ah: 9958 ONLY -- Horizontal Offset, High (character units)
|
||
Bit 7 6 5 4 3 2 1 0
|
||
Name 0 0 HO8 HO7 HO6 HO5 HO4 HO3
|
||
The screen is shifted TO THE LEFT as specified in 8-dot units (16-dot units in
|
||
Screen 6-7).
|
||
When SP2=0: Scrolling is done within one page and the non-displayed left side
|
||
of the page is displayed on the right hand side of the screen (HO8 is ignored
|
||
in this mode).
|
||
When SP2=1: Scrolling is done within 2 pages, and when scrolled, the second
|
||
page appears to the right habd side of the first page, and when scrolled more,
|
||
the first page reappears to the right of the second page. Note: When SP2=1,
|
||
the A15 bit of the Pattern Name table base address register should be set to
|
||
"1" (VDP Register 02h, Bit 5), otherwise only the leftmost page would be
|
||
displayed.
|
||
|
||
Register 1Bh: 9958 ONLY -- Horizontal Offset, Low (dot units)
|
||
Bit 7 6 5 4 3 2 1 0
|
||
Name 0 0 0 0 0 HO2 HO1 HO0
|
||
The screen is shifted TO THE RIGHT (unlike as for Register 1Ah which shifts to
|
||
the left) as specified in 1-dot units (2-dot units in Screen 6-7). When this
|
||
register is set to a non-zero value, the colors of the leftmost pixel(s) will
|
||
be undefined, to avoid this dirt effect, the MSK bit must be set, the leftmost
|
||
8 pixels (16 pixels in Screen 6-7) will be then covered by the border color.
|
||
|
||
YJK=0 (YAE=Ignored) - Normal RGB Mode
|
||
When YJK is set to zero, colors are generated identically as on MSX2. Ie.
|
||
Screen 0-7 Background and Sprites are colorized by the 3/3/3 bit RGB values
|
||
that are defined in the Palette Registers. Screen 8 background is using
|
||
hardcoded 3/3/2 bit RGB values for background, and hardcoded (1/1/1)*2 bit
|
||
colors for sprites.
|
||
|
||
YJK=1 and YAE=0 - YJK Without Attribute
|
||
A group of 4 bytes defines the colors of 4 continuous dots (horizontally).
|
||
Bit Dot 0 Dot 1 Dot 2 Dot 3
|
||
0-2 KL KH JL JH Shared J and K values for all dots
|
||
3-7 Y1 Y2 Y3 Y4 Separate Y values for each dot
|
||
Each of the four pixels is having its own "Y" value (5 bits), the "J" and "K"
|
||
values (6 bits each) are shared for all four pixels. It is possible to select
|
||
between 131072 colors (17 bits), even though each 4 pixels must have similiar
|
||
colors.
|
||
When YJK=1: Sprites in Screen 8 using RGB colors from Palette Registers!
|
||
|
||
YJK=1 and YAE=1 - YJK (and RGB) With Attribute
|
||
A group of 4 bytes defines the colors of 4 continuous dots (horizontally).
|
||
Bit Dot 0 Dot 1 Dot 2 Dot 3
|
||
0-2 KL KH JL JH Shared J and K values for all dots
|
||
3 A A A A Attribute for each dot
|
||
4-7 Y1 Y2 Y3 Y4 Separate Y values for each dot
|
||
When A=0: Colors are generated as when YAE=0, except that only 65536 colors
|
||
(16 bits) can be selected because Y-values are reduced to 4 bits.
|
||
When A=1: Y is used as color code, selecting one of the 16 RGB colors that are
|
||
defined in the palette registers. K and L values are not used.
|
||
When YJK=1: Sprites in Screen 8 using RGB colors from Palette Registers!
|
||
|
||
Formulas for YJK / RGB conversion
|
||
RGB to YJK: J=R-Y, K=G-Y, Y=B/2+R/4+G/8
|
||
YJK to RGB: R=Y+J, G=Y+K, B=Y*5/4-J/2-K/4
|
||
Note: Even though up to 131072 colors could be selected by YJK codes, the
|
||
resulting RGB values are cut down to 5 bits each, so that not more than 32768
|
||
colors can be displayed in practice.
|
||
|
||
WTE - Bit 2 - Wait Function Enable
|
||
When WTE is cleared, access to VRAM works in the same way as V9938, ie. the
|
||
programmer must take care about inserting delays between each VRAM access.
|
||
The WAIT function is enabled when WTE is set. When the CPU accesses the VRAM,
|
||
any following CPU access to any V9958 ports is offhold by a WAIT signal until
|
||
the VRAM access is completed. (This feature is supposed to speed up the
|
||
writing time of data from CPU to VRAM.)
|
||
However, WAIT function is provided after VRAM access only, not after access to
|
||
any VDP registers, any VDP status registers, or VDP palette registers.
|
||
|
||
VDS - Bit 5 - Output selection between CPUCLK and /VDS
|
||
Unlike V9938, the V9958 video chip doesn't have two separate pins for CPUCLK
|
||
and /VDS signals, instead a single pin is shared for both signals. By default
|
||
CPUCLK is output, alternately, /VDS can be output by setting the VDS bit.
|
||
(Using /VDS mode in MSX offers no known advantages, but it is reported to
|
||
confuse some TV tuners and thus shouldn't be used.)
|
||
|
||
CMD - Bit 6 - Command Function
|
||
Normally MSX2 Video Commands (VDP Registers 20h-2Eh) can be used in Screen 5-8
|
||
only. However, by setting the CMD bit Video Commands may be used in all other
|
||
Screen modes. In these 'additional' modes, Video Commands are accessing VRAM
|
||
bytewise (as in Screen 8), therefore X/Y coordinates as in Screen 8 must be
|
||
used. (The CMD bit has no influence in Screen 5-8.)
|
||
|
||
Deleted Functions
|
||
The V9958 does not output a Composite Video Signal, and does not include a
|
||
Mouse/Lightpen Interface. In the result, the following bits have been removed
|
||
(and should be set to zero): Bit 5 of VDP Reg 00h (IE2), Bit 6 and 7 of VDP
|
||
Reg 08h (LP and MS), Bit 6 and 7 of VDP Status Reg 01h (LPS and FL).
|
||
|
||
VDP Registers 20h-2Eh: MSX2 Video Command Registers
|
||
---------------------------------------------------
|
||
|
||
The VDP Registers 20h-2Eh are related to MSX2 Video Commands.
|
||
Registers below available in MSX2, MSX2+, and turbo R only.
|
||
|
||
Register 20h: Source X Low byte (0-FF)
|
||
Register 21h: Source X High byte (0-1)
|
||
Register 22h: Source Y Low byte (0-FF)
|
||
Register 23h: Source Y High byte (0-3)
|
||
Register 24h: Destination X Low byte (0-FF)
|
||
Register 25h: Destination X High byte (0-1)
|
||
Register 26h: Destination Y Low byte (0-FF)
|
||
Register 27h: Destination Y High byte (0-3)
|
||
Register 28h: Number of X dots low byte (0-FF)
|
||
Register 29h: Number of X dots high byte (0-3)
|
||
Register 2Ah: Number of Y dots low byte (0-FF)
|
||
Register 2Bh: Number of Y dots high byte (0-3)
|
||
|
||
Register 2Ch: Data
|
||
Bit Name Expl.
|
||
0-7 CL Color Code
|
||
For high speed commands, all bits are used, ie. in screen 5-7 more than one
|
||
pixel can be transferred at once. For all other commands, only one pixel can
|
||
be specified at once, so in screen 5-7 only the lower 2 or 4 bits of the
|
||
register are used.
|
||
|
||
For VDP -> VRAM commands, all pixel(s) are colorized in the same color,
|
||
which must have been written to this register before the command started.
|
||
|
||
For CPU -> VRAM commands, each pixel (or byte in highspeed mode) must be
|
||
written to this register separately, whereas the first pixel (or byte) should
|
||
be written <before> the command gets started! When the command has been
|
||
started, bit 7 of VDP status register 2 indicates whether the VDP controller
|
||
is ready to receive the next value, and bit 0 indicates if the command has
|
||
been completed.
|
||
|
||
Register 2Dh: Argument register
|
||
Bit Name Expl.
|
||
0 MAJ Longest side (Line command) (0=Normal, 1=Exchange X/Y-Len)
|
||
1 EQ Equal (For Search command) (0=Repeat until equal, 1=not equal)
|
||
2 DIX X step direction (0=right, 1=left)
|
||
3 DIY Y step direction (0=down, 1=up)
|
||
4 MXS Source external memory (0=128K VRAM, 1=64K external)
|
||
5 MXD Destination external memory (0=128K VRAM, 1=64K external)
|
||
6 MXC CPU Access external memory (0=128K VRAM, 1=64K external)
|
||
7 0 Always 0
|
||
By default MSX2 computers are equipped with 128K VRAM, but the system could by
|
||
upgraded to additional 64K external VRAM. This additional RAM resides in the
|
||
same address space as the 1st 64K normal VRAM, bit 4-6 are used to access
|
||
external memory.
|
||
The external VRAM cannot be displayed directly - but it can be used as
|
||
additional workspace for VDP commands by setting the MXS and/or MXD bit(s).
|
||
External memory could be also read/written through port 98h by setting the MXC
|
||
bit.
|
||
|
||
Register 2Eh: Command register
|
||
Bit Name Expl.
|
||
0-2 AR0-2 Logical argument, see below. ignored by highspeed commands
|
||
3 TRN Transparent (1=Transparent Color 0) ignored by highspeed commands
|
||
4-7 C0-3 Command, see below.
|
||
Commands (C0-C3):
|
||
Value: Expl.:
|
||
0 Stop
|
||
4 Get Pixel, VRAM -> VDP
|
||
5 Put Pixel, VDP -> VRAM
|
||
6 Search Pixel, VRAM -> VRAM
|
||
7 Draw Line, VDP -> VRAM
|
||
8 Logical Fill Rectangle, VDP -> VRAM
|
||
9 Logical Copy Rectangle, VRAM -> VRAM
|
||
A Logical Get Pixels, VRAM -> CPU
|
||
B Logical Put Pixels, CPU -> VRAM
|
||
C Highspeed Fill Rectangle, VDP -> VRAM
|
||
D Highspeed Copy Rectangle, VRAM -> VRAM
|
||
E Highspeed Copy Vertically, VRAM -> VRAM
|
||
F Highspeed Put Bytes, CPU -> VRAM
|
||
Arguments (AR0-AR2) (ignored by highspeed commands):
|
||
Value: Name: Expl.:
|
||
0 PSET Set bits, set old bits to 0
|
||
1 AND Mask bits
|
||
2 OR Set bits, include old
|
||
3 XOR Swap new bits
|
||
4 NOT Set new bits to 0
|
||
|
||
Notes about above 'VDP' and 'CPU' Expressions
|
||
'CPU' in the above table means that the commands expects more than one value
|
||
to be read/written manually by the program. And 'VDP' means that only one
|
||
value is expected to be read/written by the program. In both cases, data is
|
||
written through VDP Register 2Ch, or read through status register 07h.
|
||
|
||
Notes about X-Loc and X-Len
|
||
Highspeed commands always copy whole bytes, so in screen 6-7 the lower bit(s)
|
||
of the X-Loc and X-Len operands have no effect.
|
||
For the Fill and Copy Commands, a horizontal length of zero is treated as
|
||
maximum length (that is distance from origin to screen border).
|
||
|
||
Vertical Copy Command
|
||
For the 'Vertical' Copy command, the source X-Loc operand is ignored (the
|
||
destination X-Loc operand is used for both source and destination). Also, the
|
||
X-Len operand is ignored (Instead distance from origin to end of screen is
|
||
used as horizontal length). Otherwise the command is quite the same as the
|
||
Copy Rectangle command, probably a good bit faster though.
|
||
|
||
Notes about Line Command
|
||
For the 'Line' command, the greater value of the X-Len and Y-Len operands must
|
||
be always placed into Register 28h and 29h (Major Length) and the smaller
|
||
value must be placed into Register 2Ah and 2Bh (Minor Length).
|
||
For 'vertical' lines, bit 0 of VDP Register 2Dh must be set to indicate that
|
||
Register 28h and 29h refer to the Y-Len.
|
||
Also note that the length values for the Line command specify the relocation
|
||
from the origin, so a length of 0;0 would draw a single dot. The function
|
||
allows to draw diagonal lines at any angle.
|
||
|
||
Display Timings
|
||
---------------
|
||
|
||
Horizontal Timings
|
||
Scanline Time : 227.75 cycles
|
||
Scanline Rate : 15716.99 Hz
|
||
|
||
Vertical Timings, 50Hz Mode
|
||
Frame Height : 313 scanlines
|
||
Frame Time : 71285.75 cycles
|
||
Exact Frame Rate : 50.214 Hz
|
||
Possible HBL IRQs: Line 00-FF (either 192/212 pix mode)
|
||
|
||
Vertical Timings, 60Hz Mode
|
||
Frame Height : 262 scanlines
|
||
Frame Time : 59670.5 cycles
|
||
Exact Frame Rate : 59.9885 Hz
|
||
Possible HBL IRQs: Line 00-EA (192 pix mode), 00-F4 (212 pix mode)
|
||
|
||
Above 'cycles' are meant to be counted in CPU clock cycle units, ie.
|
||
3.579545MHz units.
|
||
|
||
VDP Interrupts
|
||
--------------
|
||
|
||
Interrupt Sources
|
||
The MSX2 includes two interrupt sources: VBlank and HBlank interrupts. For
|
||
MSX1 only the VBlank interrupt source exist.
|
||
A VBlank interrupt is requested each time when the VDP begins to draw the
|
||
lower screen border (ie. in scanline 192 or 212, depending on the vertical
|
||
screen resolution).
|
||
A HBlank interrupt is requested when the VDP draws the scanline specified in
|
||
VDP register 13h, this might be any of the 192 or 212 scanlines of the picture
|
||
- or one of the following scanlines in the lower screen border section.
|
||
Multiple HBlank Interrupts can be generated by re-writing VDP Register 13h
|
||
several times per frame.
|
||
|
||
Interrupt Enable Flags
|
||
VBlank and HBlank interrupts can be separately enabled/disabled by bits in VDP
|
||
Registers 0 and 1. In case that the Z80 has disabled interrupts by clearing
|
||
the IFF flag (for example by a "DI" instruction) then this becomes priority
|
||
and VDP interrupt enable flags are ignored even if set.
|
||
|
||
Interrupt Requests
|
||
The VDP requests interrupts by setting the Vblank or Hblank IRQ flags in VDP
|
||
Status Register 0 and 1 each time when an interrupt condition becomes true.
|
||
This happens even if interrupts are disabled by the IFF flag and/or by the
|
||
VBlank interrupt enable flags, however, HBlank IRQs are NOT requested if the
|
||
HBlank interrupt flag is cleared.
|
||
|
||
Interrupt Execution
|
||
An interrupt is executed only when all of the following conditions are true:
|
||
The CPU must have enabled interrupts by setting IFF=1. Either the VBlank or
|
||
HBlank interrupt must be enabled in VDP register 0 or 1, and the respective
|
||
VBlank or HBlank IRQ flag must be set in VDP Status Register 0 or 1.
|
||
The interrupt handler is executed at the time when the above conditions become
|
||
true. This might directly upon IRQ request in case that the enable flags were
|
||
set - or directly upon enabling interrupts in case that an IRQ flag was set.
|
||
|
||
Acknowleding Interrupts
|
||
The interrupt handler MUST manually acknowlede interrupts by reading from the
|
||
respective VDP status register(s) which contain the IRQ flag(s). Otherwise the
|
||
IRQ flag(s) are kept set, causing the same interrupt to be kept requested -
|
||
which would be then executed again at the next time when interrupts are
|
||
enabled.
|
||
|
||
Sound Generator
|
||
---------------
|
||
|
||
I AY-3-8910 Programmable Sound Generator (PSG)
|
||
|
||
Port A0 PSG Index 00-0Fh (Write Only)
|
||
Port A1 PSG Data Write
|
||
Port A2 PSG Data Read
|
||
|
||
The AY-3-8910 is a I/O chip with 3 sound generators.
|
||
It controls the three MSX standard audio channels, joystick and cassette.
|
||
|
||
PSG Registers 00-0Fh are:
|
||
|
||
00 = Frequency channel A, low (0-255)
|
||
01 = Frequency channel A, high (0-15)
|
||
02 = Frequency channel B, low (0-255)
|
||
03 = Frequency channel B, high (0-15)
|
||
04 = Frequency channel C, low (0-255)
|
||
05 = Frequency channel C, high (0-15)
|
||
The actual listened frequency in Hertz is calculated as follows:
|
||
F = 3.579545MHz / 32 / nn ;with nn in range 0..4095
|
||
|
||
06 = Noise period (0-31)
|
||
The actual noise frequency in Hertz is calculated as follows:
|
||
F = 3.579545MHz / 32 / nn ;with nn in range 0..31
|
||
|
||
07 = Mixer
|
||
Bit Expl.
|
||
0 Channel A tone enable (0=Enable,1=Disable)
|
||
1 Channel B tone enable (0=Enable,1=Disable)
|
||
2 Channel C tone enable (0=Enable,1=Disable)
|
||
3 Channel A noise enable (0=Enable,1=Disable)
|
||
4 Channel B noise enable (0=Enable,1=Disable)
|
||
5 Channel C noise enable (0=Enable,1=Disable)
|
||
6 I/O port A mode (0=Input, 1=Output)
|
||
7 I/O port B mode (0=Input, 1=Output)
|
||
|
||
08 = Volume channel A (0-15, 16=Envelope)
|
||
09 = Volume channel B (0-15, 16=Envelope)
|
||
0A = Volume channel C (0-15, 16=Envelope)
|
||
|
||
0B = Envelope Frequency, low (0-255)
|
||
0C = Envelope Frequency, high (0-255)
|
||
Envelope step frequency (tone or noise) calculated as follows:
|
||
F = 3.579545MHz / 32 / nn ;with nn in range 0..65535
|
||
Depending on the envelope shape, the volume is incremented from 0 to 15, or
|
||
decremted from 15 to 0. In either case it takes 16 steps to complete, the
|
||
completion time for 16 steps is therefore:
|
||
T = nn*512 / 3.579545MHz ;with nn in range 0..65535 (0-9.37 seconds)
|
||
|
||
0D = Envelope shape (0-15)
|
||
CONT ATT ALT HLD
|
||
0 0 X X \_________ 0-3 (same as 9)
|
||
0 1 X X /_________ 4-7 (same as F)
|
||
1 0 0 0 \\\\\\\\\\ 8 (Repeating)
|
||
1 0 0 1 \_________ 9
|
||
1 0 1 0 \/\/\/\/\/ A (Repeating)
|
||
1 0 1 1 \""""""""" B
|
||
1 1 0 0 ////////// C (Repeating)
|
||
1 1 0 1 /""""""""" D
|
||
1 1 1 0 /\/\/\/\/\ E (Repeating)
|
||
1 1 1 1 /_________ F
|
||
|
||
0E = I/O port A (Joystick and Cassette Input)
|
||
Bit Expl.
|
||
0 Joystick Up (0=Moved, 1=Not moved)
|
||
1 Joystick Down (0=Moved, 1=Not moved)
|
||
2 Joystick Left (0=Moved, 1=Not moved)
|
||
3 Joystick Right (0=Moved, 1=Not moved)
|
||
4 Joystick button A (0=Pressed, 1=Not pressed)
|
||
5 Joystick button B (0=Pressed, 1=Not pressed)
|
||
6 Keyboard Switch (Japanese SVI machines only ?)
|
||
7 Cassette input
|
||
|
||
0F = I/O port B (Joystick Select Output)
|
||
Bit Expl.
|
||
0 1 (Used as handshaking output if touchpad)
|
||
1 1 (Used as handshaking output if touchpad)
|
||
2 1 (Used as handshaking output if touchpad)
|
||
3 1 (Used as handshaking output if touchpad)
|
||
4 Pulse 1 (Positive pulse starting a monostable timer)
|
||
5 Pulse 2 (Positive pulse starting a monostable timer)
|
||
6 Joystick select (0=Connector 1, 1=Connector 2)
|
||
7 LED Code LED, if any (0=On, 1=Off)
|
||
|
||
Bits 4 and 5 is used by a program which uses a paddle (analog-joystick). A
|
||
short positive edge pulse on bit 4 (or 5) starts a monostable timer (in the
|
||
attached paddle) and the paddle sets one of the joystick bits in register 14
|
||
low (FIRE A (FIRE B),L,R,D or U). When the monostable times out, the joystick
|
||
bit in port 14 is set high again. The length of the counting period of the
|
||
monostable timer is set (in the attached paddle) by a variable resistor. The
|
||
computer can determine the position of the variable resistor by measuring the
|
||
time while the joystick bit in register 14 is low.
|
||
The Code LED is included in models that have a locking function for the CODE
|
||
key, such like Japanese, Russian, or Korean models which are enabling the
|
||
native character set by that key, and by some US/European MSX1 BIOSes.
|
||
Otherwise, if the Code key is active only when held down, no Code LED is
|
||
included.
|
||
|
||
Cartridge Memory Mappers
|
||
------------------------
|
||
|
||
Raw ROM without Mapper
|
||
Small cartridges with only 32Kbytes or less ROM aren't including memory
|
||
mappers, these ROMs typically occupy the address space at 4000-BFFF.
|
||
Memory Content (not mappable)
|
||
0000-3FFF sometimes mirror of 1st 16KB of ROM
|
||
4000-7FFF 1st 16KB of ROM
|
||
8000-BFFF 2nd 16KB of ROM (eventually 1st 16K if size less than 32K)
|
||
Theoretically 64K ROMs aren't requiring a memory mapper as they could occupy
|
||
the whole address space from 0000-FFFF, however, for whatever reason, most or
|
||
all 64K ROMs are using Ascii 16K mappers.
|
||
|
||
Konami 8K without SCC
|
||
This type is used by Konami cartridges that do not have a SCC and some others.
|
||
Memory Mapper I/O Address
|
||
4000-5FFF fixed, always bank 0
|
||
6000-7FFF select bank by writing to 6000
|
||
8000-9FFF select bank by writing to 8000
|
||
A000-BFFF select bank by writing to A000
|
||
|
||
Konami 8K with SCC
|
||
This type is used by Konami cartridges that do have a SCC and some cartridges
|
||
not made by Konami (and that are NOT including a SCC ?).
|
||
Memory Mapper I/O Address
|
||
4000-5FFF select bank by writing to 5000-57FF (5000 used)
|
||
6000-7FFF select bank by writing to 7000-77FF (7000 used)
|
||
8000-9FFF select bank by writing to 9000-97FF (9000 used)
|
||
A000-BFFF select bank by writing to B000-B7FF (B000 used)
|
||
If it is a Konami cartridge, you can use the SCC ("Sound Custom Chip") by
|
||
writing a value with bits 0-5 set (3Fh, bits 6 and 7 do not matter) to
|
||
9000h-97FFh, you can then read and write to the SCC in the memory area
|
||
9800h-AFFFh.
|
||
|
||
ASCII 8KB
|
||
Used by various games. A few cartridges of this type may also contain 8K SRAM,
|
||
which is selected by setting one of the upper bank number bits. (For example,
|
||
bank=20h for Xanadu, bank=80h for Royal Blood.)
|
||
Memory Mapper I/O Address
|
||
4000-5FFF select bank by writing to 6000-67FF (6000 used)
|
||
6000-7FFF select bank by writing to 6800-6FFF (6800 used)
|
||
8000-9FFF select bank by writing to 7000-77FF (7000 used)
|
||
A000-BFFF select bank by writing to 7800-7FFF (7800 used)
|
||
Note that writing to 6000-7FFF is used for mapper I/O, therefore SRAM can be
|
||
only written to when mapped to 8000-9FFF or A000-BFFF (or maybe also 4000-5FFF
|
||
?).
|
||
|
||
ASCII 16KB
|
||
Among others this type is often used by many 64KB cartridges.
|
||
Memory Mapper I/O Address
|
||
4000-7FFF select bank by writing to 6000-67FF (or 6000-6FFF ?) (6000 used)
|
||
8000-BFFF select bank by writing to 7000-77FF (or 7000-7FFF ?) (7000 used)
|
||
The game Hydlide 2 also includes 2KB of SRAM (selected by bank number 10h),
|
||
SRAM can be written to only when mapped to 8000-BFFF, the SRAM is mirrored to
|
||
all 2K fragments of the 16K bank.
|
||
|
||
Other Mappers
|
||
A few cartridges are using their own exotic memory mappers which aren't
|
||
described here, just note that the above standards do not apply for all
|
||
cartridges.
|
||
|
||
Floppy Disk Controller
|
||
----------------------
|
||
|
||
Disk based MSX computers are typically using a Western Digital FD1793 Floppy
|
||
Disk Controller (FDC). MSX2 computers are (usually) including a built-in disk
|
||
drive, and diskless MSX1 computers can be upgraded by external disk drives.
|
||
|
||
--> FDC I/O Addresses
|
||
--> FDC Description
|
||
--> Disk FAT Format
|
||
|
||
FDC I/O Addresses
|
||
-----------------
|
||
|
||
Disk drives have not been part of the first MSX computers, and obviously
|
||
different companies invented their own disk adapters independendly of each
|
||
other. In result there are a couple of different 'world standards'.
|
||
|
||
Described below are different memory-mapped and I/O-based addresses, that are
|
||
used by different adapters. (For memory mapped adapters the Disks PSLOT
|
||
(and/or SSLOT) must be selected, the addresses may then be accessed by LD
|
||
commands. Less popular I/O based adapters are accessed by IN and OUT
|
||
commands.)
|
||
|
||
7FFX - Memory mapped IO addresses
|
||
Used by various distributors: Sharp, Philips, ACVS/CIEL.
|
||
7FF8h R Status Register
|
||
7FF8h W Command Register
|
||
7FF9h R/W Track Register
|
||
7FFAh R/W Sector Register
|
||
7FFBh R/W Data Register
|
||
7FFCh R?/W Side (bit 0) Motor here?
|
||
7FFDh R ??
|
||
7FFDh W Drive (bit 0) Motor here?
|
||
7FFEh - Unused
|
||
7FFFh R Data Request (bit 7), Busy (bit 6)
|
||
Note: MSX-DOS/BarbarianLoader selects memory at 8000-BFFF into the disks
|
||
PSLOT, and then accesses the disk via addresses BFFX rather than 7FFX.
|
||
|
||
7FBX - Memory mapped IO addresses for a SV738 (X'press) disk
|
||
These addresses are used by 'Technoahead' disk BIOS.
|
||
7FB8h R Status Register
|
||
7FB8h W Command Register
|
||
7FB9h R/W Track Register
|
||
7FBAh R/W Sector Register
|
||
7FBBh R/W Data Register
|
||
7FBCh R IRQ/Not Busy (bit 7), Data Request (bit 6)
|
||
7FBCh W Select Drive 0/1 (bit 0/1), Side (bit 2), Motor (bit 3)
|
||
7FBDh-Fh - Unused
|
||
|
||
7F8X - Memory mapped IO addresses for Arabic Disk ROM
|
||
Same as above 7FB8-7FBC, but using addresses 7F80-7F84 instead.
|
||
|
||
I/O Ports for Brazilian Disk ROMs
|
||
Used by various (brazilian only) distributors: Digital Design Electronica
|
||
Ltda, Conector Informatica, Microsol Tecnologia, Liftrom Informatica.
|
||
D0h R Status Register
|
||
D0h W Command Register
|
||
D1h R/W Track Register
|
||
D2h R/W Sector Register
|
||
D3h R/W Data Register
|
||
D4h W Drive (bit 1), Side (bit 4), Motor (bit ??)
|
||
D4h R IRQ/Not Busy (bit 7), Data Request (bit 6) (V3.0 and up)
|
||
D5h-D7h - Unused
|
||
Note: Reading from Port D4h required/supported by V3.0 or newer interfaces
|
||
only, older devices used status register bits 0 and 1 which have identical
|
||
meaning.
|
||
V2.7 and newer are reported to be "Mixed Port and Memory Based", however,
|
||
these Disk BIOS versions appear to include Port Based code only, but possibly
|
||
the hardware itself recognizes Memory Based software?
|
||
|
||
Note: As you may have noticed, the first four Memory Addresses or I/O Ports
|
||
are always controlling the Status/Command, Track, Sector, and Data Registers,
|
||
that is because these addresses are directly accessing the FDC registers. The
|
||
four higher addresses control custom, non-standard circuits made by the drive
|
||
manufacturer.
|
||
|
||
FDC Description
|
||
---------------
|
||
|
||
Command description
|
||
Commands should only be loaded in the Command Register when the Busy status
|
||
bit is off (Status bit 0). The one exception is the Force Interrupt command.
|
||
Whenever a command is being executed, the Busy status bit is set.
|
||
At the completion of every command an INTRQ is generated. INTRQ is reset by
|
||
either reading the status register or by loading the command register with a
|
||
new command. In addition, INTRQ is generated if a Force Interrupt command
|
||
condition is met.
|
||
When a command is completed, an interrupt is generated and the busy status bit
|
||
is reset. The Status Register indicates whether the completed command
|
||
encountered an error or was fault free.
|
||
|
||
Command Summary (models 1791, 1792, 1793, 1794)
|
||
Type Command b7 b6 b5 b4 b3 b2 b1 b0
|
||
I Restore 0 0 0 0 h V r1 r0
|
||
I Seek 0 0 0 1 h V r1 r0
|
||
I Step 0 0 1 T h V r1 r0
|
||
I Step-In 0 1 0 T h V r1 r0
|
||
I Step-Out 0 1 1 T h V r1 r0
|
||
II Read Sector 1 0 0 m S E C 0
|
||
II Write Sector 1 0 1 m S E C a0
|
||
III Read Address 1 1 0 0 0 E 0 0
|
||
III Read Track 1 1 1 0 0 E 0 0
|
||
III Write Track 1 1 1 1 0 E 0 0
|
||
IV Force Interrupt 1 1 0 1 i3 i2 i1 i0
|
||
|
||
Flag Summary
|
||
r1,r0 Stepping Motor Rate (0: 6ms, 1: 12ms, 2: 20ms, 3: 30 ms)
|
||
V Track Number Verify Flag (0: no verify, 1: verify on dest track)
|
||
h Head Load Flag (1: load head at beginning, 0: unload head)
|
||
T Track Update Flag (0: no update, 1: update Track Register)
|
||
a0 Data Address Mark (0: FB, 1: F8 (deleted DAM))
|
||
C Side Compare Flag (0: disable side compare, 1: enable side comp)
|
||
E 15 ms delay (0: no 15ms delay, 1: 15 ms delay)
|
||
S Side Compare Flag (0: compare for side 0, 1: compare for side 1)
|
||
m Multiple Record Flag (0: single record, 1: multiple records)
|
||
Interrupt Condition Flags
|
||
i3-i0 0 = Terminate with no interrupt (INTRQ)
|
||
i3 1 = Immediate interrupt, requires a reset
|
||
i2 1 = Index pulse
|
||
i1 1 = Ready to not ready transition
|
||
i0 1 = Not ready to ready transition
|
||
|
||
Type I commands (Restore, Seek, Step-Out, Step-In, Step)
|
||
Used to move the read/write head. The stepping motor rate should be usally set
|
||
to 6ms (r1 and r0 bits set to zero) for a 3.5-inch floppy disk drive. An
|
||
optional verification of head position can be performed by setting bit 2 (V=1)
|
||
in the command word.
|
||
|
||
When V=1: When the seek is completed, the drive automatically goes into read
|
||
mode, the track number from the first encountered Sector ID Field is then
|
||
compared against the contents of the Track Register (or Data Register?), if
|
||
the track numbers compare (and the ID Field CRC is correct) the verify
|
||
operation is complete and an INTRQ is generated with no errors. If these track
|
||
numbers do not match, the Seek Error bit of the status register is set.
|
||
|
||
When V=0: When the seek is completed, the track position is not verified (this
|
||
mode is required for unformatted disks). The command ends once the last step
|
||
pulse is output. Since the result is that there is not enough time for step
|
||
stability, the host system must use its software to make the floppy disk wait
|
||
a certain period before reading or writing the track just arrived at.
|
||
|
||
When the seek command is complete, the interrupt request is set and at the
|
||
same time, the Busy bit in the status register is set to 0. When the CPU reads
|
||
the status register, it resets the interrupt request signal.
|
||
|
||
Restore (Seek Track 0)
|
||
If TR00 is not active, stepping pulses are issued until the TR00 input is
|
||
activated. The Track Register is set to zero, and an interrupt is generated
|
||
when track 0 has been reached.
|
||
|
||
Seek
|
||
This command assumes that the Track Register contains the <current> position
|
||
of the head, and that the Data Register contains the <desired> destination
|
||
track number.The FD179X will update the Track Register and issue stepping
|
||
pulses in the appropriate direction until the contents of the Track and Data
|
||
Register are equal to each other. An interrupt is generated at the completion
|
||
of the command.
|
||
|
||
Step-Out, Step-In, Step
|
||
Issues one stepping pulse to the disk drive. Step-Out: towards track 0.
|
||
Step-In: towards track 76. Step: same direction as for previous step command.
|
||
The track register is updated (ie. incremented or decremented) only if the "T"
|
||
bit has been set in the command word. An interrupt is generated at the end of
|
||
each command.
|
||
|
||
Type II commands (Read Sector, Write Sector)
|
||
Prior to loading the Type II command into the Command Register, the computer
|
||
must load the Sector Register with the desired sector number. Upon receipt of
|
||
the Type II command, the busy status bit is set. The FD179X must find an ID
|
||
field with a matching Track number and Sector number, otherwise the Record not
|
||
found status bit is set and the command is terminated with an interrupt.
|
||
Each of the Type II commands contains an m flag which determines if multiple
|
||
records (sectors) are to be read or written. If m=0, a single sector is read
|
||
or written and an interrupt is generated at the completion of the command. If
|
||
m=1, multiple records are read or written with the sector register internally
|
||
updated so that an address verification can occur on the next record. The
|
||
FD179X will continue to read or write multiple records and update the sector
|
||
register in numerical ascending sequence until the sector register exceeds the
|
||
number of sectors on the track or until the Force Interrupt command is loaded
|
||
into the Command Register.
|
||
The Type II commands for 1791-94 also contain side select compare flags. When
|
||
C=0 (bit 1), no comparison is made. When C=1, the LSB of the side number is
|
||
read off the ID Field of the disk and compared with the contents of the S
|
||
flag.
|
||
|
||
Read Sector
|
||
Upon receipt of the command, the head is loaded, the busy status bit set and
|
||
when an ID field is encountered that has the correct track number, correct
|
||
sector number, correct side number, and correct CRC, the data field is
|
||
presented to the computer.
|
||
An DRQ is generated each time when the CPU must read a byte from the data
|
||
register, the Lost Data bit is set if the CPU didn't read data in time, and
|
||
the Read operation continues until the end of sector is reached.
|
||
At the end of the Read operation, the type of Data Address Mark encountered in
|
||
the data field is recorded in the Status Register (bit 5).
|
||
|
||
Write Sector
|
||
Upon receipt of the command, the head is loaded, the busy status bit set and
|
||
when an ID field is encountered that has the correct track number, correct
|
||
sector number, correct side number, and correct CRC, a DRQ is generated.
|
||
The FD179X counts off 22 bytes (in double density) from the CRC field and the
|
||
Write Gate output is made active if the DRQ is serviced (ie. the DR has been
|
||
loaded by the computer). If DRQ has not been serviced, the command is
|
||
terminated and the Lost Data status bit is set. If the DRQ has been serviced,
|
||
12 bytes of zeroes (in double density) are written to the disk, then the Data
|
||
Address Mark as determined by the a0 field of the command.
|
||
The FD179X then writes the data field and generates DRQ's to the computer. If
|
||
the DRQ is not serviced in time for continuous writing the Lost Data Status
|
||
bit is set and a byte of zeroes is written on the disk and the command
|
||
continues until the last byte of the sector is reached.
|
||
After the last data byte has been written on the disk, the two-byte CRC is
|
||
computed internally and written on the disk followed by one byte of logic
|
||
ones.
|
||
|
||
Type III commands
|
||
|
||
Read Address
|
||
Upon receipt of the Read Address command, the head is loaded and the Busy
|
||
Status bit is set. The next encountered ID field is then read in from the
|
||
disk, and the six data bytes of the ID field are assembled and transferred to
|
||
the DR, and a DRQ is generated for each byte. The six bytes of the ID field
|
||
are : Track address, Side number, Sector address, Sector Length, CRC1, CRC2.
|
||
Although the CRC bytes are transferred to the computer, the FD179X checks for
|
||
validity and the CRC error status bit is set if there is a CRC error. The
|
||
track address of the ID field is written into the sector register so that a
|
||
comparison can be made by the user. At the end of the operation, an interrupt
|
||
is generated and the Busy status bit is reset.
|
||
|
||
Read Track
|
||
Upon receipt of the Read Track command, the head is loaded, and the busy
|
||
status bit is set. Reading starts with the leading edge of the first
|
||
encountered index pulse and continues until the next index pulse. All gap,
|
||
header, and data bytes are assembled and transferred to the data register and
|
||
DRQ's are generated for each byte. The accumulation of bytes is synchronized
|
||
to each address mark encountered. An interrupt is generated at the completion
|
||
of the command. The ID Address Mark, ID field, ID CRC bytes, DAM, Data and
|
||
Data CRC bytes for each sector will be correct. The gap bytes may be read
|
||
incorrectly during write-splice time because of synchronization.
|
||
|
||
Write Track (formatting a track)
|
||
Upon receipt of the Write Track command, the head is loaded and the Busy
|
||
Status bit is set. Writing starts with the leading edge of the first
|
||
encountered index pulse and continues until the next index pulse, at which
|
||
time the interrupt is activated. The Data Request is activated immediately
|
||
upon receiving the command, but writing will not start until after the first
|
||
byte has been loaded into the DR. If the DR has not been loaded by the time
|
||
the index pulse is encountered, the operation is terminated making the device
|
||
Not Busy, the Lost Data status bit is set, and the interrupt is activated. If
|
||
a byte is not present in the DR when needed, a byte of zeroes is substituted.
|
||
This sequence continues from one index mark to the next index mark.
|
||
Normally, whatever data pattern appears in the data register is written on the
|
||
disk with a normal clock pattern. However, if the FD179X detects a data
|
||
pattern of F5 thru FE in the data register, this is interpreted as data
|
||
address marks with missing clocks or CRC generation. The CRC generator is
|
||
initialized when an F5 data byte is about to be transferred (in MFM). An F7
|
||
pattern will generate two CRC bytes. As a consequence, the patterns F5 thru FE
|
||
must not appear in the gaps, data fiels, or ID fiels. Tracks may be formatted
|
||
with sector lengths of 128, 256, 512 or 1024 bytes. See "Formatting" below for
|
||
more info and example.
|
||
|
||
Type IV command (Force Interrupt)
|
||
The Forced Interrupt command is generally used to terminate a multiple sector
|
||
read or write command or insure Type I status register. This command can be
|
||
loaded into the command register at any time. If there is a current command
|
||
under execution (busy status bit set), the command will be terminated and the
|
||
busy status bit reset.
|
||
|
||
Status Register
|
||
Upon receipt of any command, except the Force Interrupt command, the Busy
|
||
Status bit is set and the rest of the status bits are updated or cleared for
|
||
the new command.
|
||
The user has the option of reading the status register through program control
|
||
or using the DRQ line with DMA or interrupt methods. When the DR is read the
|
||
DRQ bit in the Status register and the DRQ line are automatically reset. A
|
||
write to the DR also causes both DRQ's to reset. The busy bit in the status
|
||
may be monitored with a user program to determine when a command is complete,
|
||
in lieu of using the INTRQ line. When using the INTRQ, a busy status check is
|
||
not recommended because a read of the status register to determine the
|
||
condition of busy will reset the INTRQ line.
|
||
|
||
Status for Type I commands
|
||
Bit Expl.
|
||
0 Busy (1=Command is in progress)
|
||
1 Index (1=Index mark detected from drive)
|
||
2 Track 0 (1=Read/Write head is positioned to Track 0)
|
||
3 CRC Error (1=CRC encountered in ID field)
|
||
4 Seek Error (1=Desired track was not verified) (reset 0 when updated)
|
||
5 Head Loaded (1=Head loaded an engaged)
|
||
6 Protected (1=Disk write protected)
|
||
7 Not Ready (1=Drive not ready)
|
||
|
||
Status for type II & III commands
|
||
Bit Expl.
|
||
0 Busy (1=Command is under execution)
|
||
1 Data Request (1=CPU must read/write next data byte) (DRQ)
|
||
2 Lost Data (1=CPU did not respond to DRQ in one byte time)
|
||
3-4 Error Code (1=Bad Data CRC, 2=Sector not found, 3=Bad ID Field CRC)
|
||
5 Fault/Type (Any Write:1=Write Fault, Read Sector:1=Deleted Data Mark)
|
||
6 Protected (Any Write:1=Write Protect, Any Read:Not used)
|
||
7 Not Ready (1=Drive not ready)
|
||
Notes: Bit 1-6 are reset when updated. Bit 3-4 not used for read/write track.
|
||
|
||
Status for type IV command
|
||
If the Force Interrupt command is received while a command is under execution,
|
||
the Busy status bit is reset and the rest of the status bits are unchanged.
|
||
If the Force Interrupt command is received when there is no command under
|
||
execution, the Busy Status bit is reset and the rest of the status bits are
|
||
updated or cleared. In this case, Status reflects the Type I commands.
|
||
|
||
External Circuit
|
||
The floppy disk controller itself cannot select the drive number, side, disk
|
||
density, and it cannot turn on/off the drive motor(s). These settings must be
|
||
set up by an external circuit, which are (as far as they aren't set to a fixed
|
||
setting) controlled through separate I/O addresses. For details have a look at
|
||
the MSX FDC I/O addresses.
|
||
|
||
Note that the FDC contains only one track register which is used for all
|
||
drives. The current track position for each drive should be backed up in
|
||
memory, and the track register should be updated each time when changing the
|
||
current drive number.
|
||
|
||
The external circuit might also use the INTRQ and DRQ lines to handle FDC
|
||
operations by DMA transfers, and/or to produce interrupts upon completion. In
|
||
the MSX these methods are not used, however, most MSX adapters allow to read
|
||
out the state of INTRQ and DRQ from a custom I/O address (this isn't actually
|
||
required because INTRQ is just a inverted copy of the Status Busy bit, and DRQ
|
||
can be read out from the normal Status register either.
|
||
|
||
Formatting
|
||
This table shows DATA PATTERNs and their FD179X interpretation in MFM.
|
||
00-F4 Write 00 thru F4
|
||
F5 Write A1, preset CRC
|
||
F6 Write C2
|
||
F7 Generate 2 CRC bytes
|
||
F8-FF Write F8 thru FF
|
||
|
||
Formatting Example
|
||
The example below shows the data stream that must be presented to the Write
|
||
Track command for the "IBM system 34 format" (256 bytes/sector), note that the
|
||
MSX usually uses 512 bytes/sector. The left values in the tables below
|
||
identify the write-repeat count (in decimal) for the values to the right.
|
||
First the Track Header must be written, followed by Sector ID and Sector Data
|
||
Fields (for each sector). Finally 4E bytes must be written until the command
|
||
has completed.
|
||
|
||
Track Header
|
||
80 x 4E
|
||
12 x 00
|
||
3 x F6 (writes C2)
|
||
1 x FC (index mark)
|
||
50 x 4E
|
||
Sector ID Field
|
||
12 x 00
|
||
3 x F5 (writes A1, preset CRC)
|
||
1 x FE (ID address mark)
|
||
1 x Track number
|
||
1 x Side number
|
||
1 x Sector number
|
||
1 x 01 (sector length=256)
|
||
1 x F7 (write 2 CRC bytes)
|
||
22 x 4E
|
||
Sector Data Field
|
||
12 x 00
|
||
3 x F5 (writes A1, preset CRC)
|
||
1 x FB (data address mark)
|
||
256 x DATA
|
||
1 x F7 (write 2 CRC bytes)
|
||
54 x 4E
|
||
Track End (Fill unused bytes)
|
||
.. x 4E
|
||
|
||
Disk FAT Format
|
||
---------------
|
||
|
||
The usual MSX floppy format is compatible to that used under DOS on PCs, with
|
||
the limitation that MSX BASIC doesn't support sub-directories. Typical formats
|
||
are 3.5", Double Density, 80 Tracks/9 Sectors, either Single Sided (360KB) or
|
||
Double Sided (720KB). The Sectors are logically numbered 01h..09h, and each
|
||
sized 200h bytes.
|
||
|
||
Boot-Record
|
||
The first sector is always used as bootsector, giving information about the
|
||
usage of the following sectors, and including the boot procedure (usually a
|
||
short program that loads MSXDOS.SYS, or just a Z80 RET opcode (C9h) if the
|
||
disk isn't bootable).
|
||
00-02 jump to 80x86 boot procedure (not used for MSX, but see below)
|
||
03-0A ascii disk name
|
||
0B-0C bytes / sector
|
||
0D sectors / cluster
|
||
0E-0F sectors / boot-record
|
||
10 number of FAT-copys
|
||
11-12 entrys / root-directory
|
||
13-14 sectors / disk
|
||
15 ID: F8=hdd, F9=3.5", FC=SS/9sec, FD=DS9, FE=SS8,FF=DS8
|
||
16-17 sectors / FAT
|
||
18-19 sectors / track
|
||
1A-1B heads / disk
|
||
1C-1D number of reserved sectors
|
||
1E-1FF MSX boot procedure (loaded to address C01Eh in RAM)
|
||
The first byte of the "jump to 80x86 boot procedure" entry must be either E9h
|
||
or EBh, otherwise the MSX BIOS ignores the MSX boot procedure at 1Eh.
|
||
|
||
FAT and FAT copy(s)
|
||
The following sectors are occupied by the File Allocation Table (FAT), which
|
||
contains 12- or 16-bit entries for each cluster:
|
||
(0)000 unused, free
|
||
(0)001 ???
|
||
(0)002... pointer to next cluster in chain (0)002..(F)FEF
|
||
(F)FF0-6 reserved (no part of chain, not free)
|
||
(F)FF7 defect cluster, don't use
|
||
(F)FF8-F last cluster of chain
|
||
Number and size of FATs can be calculated by the information in the boot
|
||
sector.
|
||
|
||
Root directory
|
||
The following sectors are the Root directory, again, size depends on the info
|
||
in bootsector. Each entry consists of 32 bytes:
|
||
00-07 Filename (first byte: 00=free entry,2E=dir, E5=deleted entry)
|
||
08-0A Filename extension
|
||
0B Fileattribute
|
||
0C-15 reserved
|
||
16-17 Timestamp: HHHHHMMM, MMMSSSSS
|
||
18-19 Datestamp: YYYYYYYM, MMMTTTTT
|
||
1A-1B Pointer to first cluster of file
|
||
1C-1F Filesize in bytes
|
||
The 'cluster' entry points to the first used cluster of the file. The FAT
|
||
entry for that cluster points to the next used cluster (if any), the FAT entry
|
||
for that cluster points to the next cluster, and so on.
|
||
|
||
Reserved Sectors (if any)
|
||
Usually the number of reserved sectors is zero, but if it has been non-zero,
|
||
then the following sector(s) are reserved (and could be used by the boot
|
||
procedure for whatever purposes for example).
|
||
|
||
Data Clusters 0002..nnnn
|
||
Finally all following sectors are data clusters. The first cluster is called
|
||
cluster number (0)002, followed by number (0)003, (0)004, and so on.
|
||
|
||
Real Time Clock
|
||
---------------
|
||
|
||
Port B4 RP 5C01 RTC Index Write
|
||
Port B5 RP 5C01 RTC Data Read/Write
|
||
|
||
This battery buffered Real Time Clock (RTC) isn't installed in all MSX
|
||
computers, it could be often found in models with built-in (or external) disk
|
||
drive.
|
||
|
||
Port 0B4h = RTC Index register (write only)
|
||
Bit Name Expl.
|
||
0-3 ? RTC register (0-15)
|
||
4-7 0 Not used
|
||
Port 0B5h = RTC data register (read/write)
|
||
Bit Name Expl.
|
||
0-3 ? RTC data read/write
|
||
4-7 0 Not used
|
||
|
||
The above index register only offers to access 16 RTC data registers, however,
|
||
beside for the time and date, the RTC chip additionally stores other data
|
||
(like the RTC/CMOS chips in PCs) and alltogether that exceeds the number of 16
|
||
4bit-registers.
|
||
The register at index D is used to sub-class registers at index 0-C into 4
|
||
blocks with contents as follows:
|
||
|
||
Block 0 Block 1 Block 2 Block 3
|
||
Index (BCD Timer) (BCD Alarm) (Screen) (Ascii)
|
||
----- ------------ ------------ ------------ ------------
|
||
0 Seconds, low --- Scratch Type
|
||
1 Seconds, hi --- X-Adjust Char 1, low
|
||
2 Minutes, low Minutes, low Y-Adjust Char 1, hi
|
||
3 Minutes, hi Minutes, hi Screen Char 2, low
|
||
4 Hours, low Hours, low Width, low Char 2, hi
|
||
5 Hours, hi Hours, hi Width, hi Char 3, low
|
||
6 Day of Week Day of Week Color, Text Char 3, hi
|
||
7 Day, low Day, low Color, BG Char 4, low
|
||
8 Day, hi Day, hi Color, Border Char 4, hi
|
||
9 Month, low --- Cas/Prn/Key Char 5, low
|
||
A Month, hi 12/24 hours Beep Frq/Vol Char 5, hi
|
||
B Year, low Leap Year Color, Title Char 6, low
|
||
C Year, hi --- Native Code? Char 6, hi
|
||
D Mode Register (Read/Write)
|
||
E Test Register (Write Only)
|
||
F Reset Register (Write Only)
|
||
|
||
Mode Register (Index 0Dh)
|
||
Bit Name Expl.
|
||
0-1 M0-1 Select Block (0-3)
|
||
2 AE Alarm enable (0=Disable, 1=Enable) (not used in MSX)
|
||
3 TE Enable Seconds (0=Freeze, 1=Active)
|
||
|
||
Test Register (Index 0Eh)
|
||
Bit Name Expl.
|
||
0 T0 Increment Seconds at a rate of 16384Hz
|
||
1 T1 Increment Minutes ""
|
||
2 T2 Increment Hours ""
|
||
3 T3 Increment Days ""
|
||
This can be used to confirm that date and time carries are done correctly.
|
||
|
||
Reset Register (Index 0Fh)
|
||
Bit Name Expl.
|
||
0 AR Reset all Alarm Registers to zero (1=Reset)
|
||
1 CR Reset fractions smaller than 1 second (1=Reset)
|
||
2 C16 Enable 16Hz clock output (0=Enable?)
|
||
3 C1 Enable 1Hz clock output (0=Enable)
|
||
Note: The clock pulse outputs aren't used in MSX.
|
||
|
||
Block 0 and 1
|
||
These blocks are used by the clock, all values are stored in BCD format. Hours
|
||
are counted from 0-23 when the 12/24 hour bit is set. Alternately hours could
|
||
count from 0-11 (AM), and then from 20-31 (PM) when 12/24 hour bit is cleared.
|
||
In the MSX the 24 hour mode is used (and any conversions to 12 hour clocks are
|
||
done by software).
|
||
The Year entry is 1980 based, ie. values 00-99 mean 1980-2079. The RTC expects
|
||
a leap year when the lower two bits of the leap year counter are zero, as the
|
||
MSX counts from 1980 onwards (which has been a leap year), the leap year
|
||
counter should be initialized identical to the lower bits of the year counter.
|
||
|
||
Block 2 and 3
|
||
These blocks may contain any custom data. The MSX2 BIOS them as follows: The
|
||
scratch byte to detect the presence of the RTC chip, the other bytes in block
|
||
2 to set up the initial video mode settings, as well as the default cassette
|
||
baud rate, key click, beep sound, etc. Block 3 may be used either to define
|
||
the Title (displayed in boot screen, type=0), or the Password (verified in
|
||
boot screen, type=1), or the BASIC Prompt (usually "Ok" ,type=2). Type 0 and 2
|
||
are stored as 6 character ascii string, type 1 is stored in form of a 16bit
|
||
CRC together with an optional 'key cartridge value'.
|
||
|
||
RS 232 Interface
|
||
----------------
|
||
|
||
The RS 232 interface (serial communications port) is accessed through Port
|
||
80h-87h, as described in the chapters below.
|
||
|
||
--> ACIA Data, Status, Mode, Command
|
||
--> Status, Interrupt Mask
|
||
--> 8253 Baud Rate Generator
|
||
|
||
Note that most MSX computers do not include a built-in RS 232 adapter.
|
||
Beside for the actual hardware, a complete MSX RS232 interface should also
|
||
include a RS232 ROM.
|
||
|
||
ACIA Data, Status, Mode, Command
|
||
--------------------------------
|
||
|
||
I8251 Asynchronous Communication Interface Adapter (ACIA)
|
||
|
||
Port 80 I8251 (ACIA) Data Register (Read/Write)
|
||
Port 81 I8251 (ACIA) Status Register (Read Only)
|
||
Port 81 I8251 (ACIA) Mode/Command Register (Write Only)
|
||
|
||
Data Register (Port 80h, Read/Write)
|
||
This port holds the byte received from RS232.
|
||
This port is also used to send bytes to RS232.
|
||
|
||
Status Register (Port 81h, Read Only)
|
||
Bit Name Desc.
|
||
0 TxRDY Transmit Ready
|
||
1 RxRDY Receive Ready (1=Received byte may be read from Port 80h)
|
||
2 TxEMPTY Transmit buffer Empty
|
||
3 PE Parity Error if 1
|
||
4 OE Overrun Error if 1 (CPU has not received character)
|
||
5 FE Framing Error if 1 (ASYNC only, STOP BIT not valid)
|
||
6 SYNDET/BRKDET SYNC/BREAK found
|
||
7 DSR Data Set Ready
|
||
|
||
Mode/Command Setup (Port 81h, Write Only)
|
||
As described below, this port is used both as Mode Setup and Command Setup
|
||
port. The configuration procedure is as follows: Output one or more zero bytes
|
||
(to ensure that the port is in Command state). Output 40h to reset the port
|
||
into Mode Setup state. Output the desired Mode Setup value. Now the port is
|
||
switched back into Command state. Output 10h to clear the error flags, and
|
||
then initialize the desired state of the TX, RX, DTR bits.
|
||
|
||
Mode Setup Register (Port 81h, Write Only, After Reset Only)
|
||
Directly after a RESET command, the MODE SETUP byte may be written:
|
||
Bit Name Expl.
|
||
0-1 BAUDFACT Baud Fact (0=Sync Mode, 1=1.8432MHz, 2=115.2kHz, 3=28.8kHz)
|
||
2-3 WORD Number of Data Bits (0=5bits, 1=6bits, 2=7bits, 3=8bits)
|
||
4 PAREN Parity Bit Enable (0=No Parity Bit, 1=One Parity Bit)
|
||
5 PARITY Parity Generation/Check (0=Odd, 1=Even)
|
||
6-7 STOP Number of Stop Bits (0=Invalid, 1=1bit, 2=1.5bits, 3=2bits)
|
||
|
||
Command Setup Register (Port 81h, Write Only, Not after Reset)
|
||
Once the MODE SETUP byte has been written, COMMAND bytes may be written:
|
||
Bit Name Expl.
|
||
0 TX Transmit Enable (0=Disable, 1=Enable)
|
||
1 DTR Set Data Terminal Ready (0=No, 1=Ready)
|
||
2 RX Receive Enable (0=Disable, 1=Enable)
|
||
3 BRK Break Operation (0=No, 1=Send Break (TxD=Low))
|
||
4 ERR_RES Reset Error Flags (0=No, 1=Reset Error Flags PE,OE,FE)
|
||
5 RTS Set Request to Send (0=No, 1=Request to Send)
|
||
6 RESET Internal Reset (0=No, 1=Reset and wait for MODE
|
||
SETUP)
|
||
7 HUNT Enter Hunt Mode (0=No, 1=Search for SYNC character)
|
||
|
||
Status, Interrupt Mask
|
||
----------------------
|
||
|
||
Port 82 RS232 Status for CTS,Timer,RI,CD (Read Only)
|
||
Port 82 RS232 Interrupt mask register (Write Only)
|
||
Port 83 RS232 ?Clock 0,1,2 read? (Read Only)
|
||
Port 83 RS232 ?Receive ready interrupt enable? (Write Only
|
||
|
||
Status for CTS,Timer,RI,CD (Port 82h, Read Only)
|
||
Bit Name Expl.
|
||
0 CD Carrier Detect (0=Active, 1=Not active)
|
||
1 RI Ring Indicator (0=Active, 1=Not active) (N/C in MSX)
|
||
6 Timer Output from i8253 Counter 2
|
||
7 CTS Clear to Send (0=Active, 1=Not active)
|
||
|
||
Interrupt Mask Register (Port 82h, Write Only)
|
||
Bit Expl.
|
||
0 Receive data ready (0=Enable Interrupt, 1=Disable)
|
||
1 Transmit data ready (0=Enable Interrupt, 1=Disable) (N/C in MSX)
|
||
2 Sync/Break found (0=Enable Interrupt, 1=Disable) (N/C in MSX)
|
||
3 i8253 channel 2 Timer (0=Enable Interrupt, 1=Disable) (N/C in MSX)
|
||
|
||
??? Clock 0,1,2 read (Port 83h, Read Only)
|
||
??? Receive ready interrupt enable (Port 83h, Write Only)
|
||
Sorry, no info. TH-AP.TXT says that Port 83h is unused.
|
||
|
||
8253 Baud Rate Generator
|
||
------------------------
|
||
|
||
Port 84 PCI i8253 Counter 0 (Receive clock)
|
||
Port 85 PCI i8253 Counter 1 (Transmit clock)
|
||
Port 86 PCI i8253 Counter 2 (Custom clock)
|
||
Port 87 PCI i8253 Mode register (Write Only)
|
||
|
||
Counter Registers (Port 84h, 85h, 86h)
|
||
The 8253 includes three 16bit counters. In the MSX RS 232 interface counter 0
|
||
and 1 are internally used to generate the Baud rates for receiving and
|
||
transmitting data, counter 2 may be used for whatever purposes (for example as
|
||
timeout counter).
|
||
|
||
The 8253 can operate at counting frequencies of up to 2MHz, in the MSX this
|
||
might be 1.8432MHz, or 115.2kHz, or 28.8kHz (depending on the the Baud Fact
|
||
value of Mode Setup byte (Port 81h). Counters are decremented at that
|
||
frequency until they become zero, and are then automatically reloaded to the
|
||
programmed reload value.
|
||
|
||
For example, a Baud Rate of 19200bps can be generated by using a counter
|
||
reload value of 0006h. Ie. 115200Hz / 6 = 19200Hz (assuming that Baud Fact has
|
||
been set to 115.2kHz). Keep in mind that the counters Read/Write mode must
|
||
have been configured before outputting the counters reload value (see Port 87h
|
||
below).
|
||
|
||
8253 Mode Register (Port 87h, Write Only)
|
||
This register actually includes three separate mode registers for each of the
|
||
three counters (addressed by the upper two bits of the written value).
|
||
Bit Expl.
|
||
0 Counter Format (0=Binary, 1=BCD)
|
||
1-3 Counter Mode (See below) (6,7=Reserved)
|
||
4-5 Prepare Read/Write (See below)
|
||
6-7 Index (Counter 0-2) (3=Reserved)
|
||
The 8253 is able to operate each counter in various modes, for the MSX RS232
|
||
interface Counter 0 and 1 (receive/transmit) should be set to mode 3 (Square
|
||
Wave), and Counter 2 (custom) should be set to mode 0. The six possible modes
|
||
are:
|
||
0 = Interrupt Generator 3 = Square Wave Generator
|
||
1 = Programmable Monoflop 4 = Trigger Output by Software
|
||
2 = Clock Pulse Generator 5 = Trigger Output by Hardware
|
||
Before reading or writing to a counter, the Read/Write mode must be
|
||
initialized. In most cases Write Mode 3 should be selected, then output both
|
||
the low byte and high byte of the desired counter reload value to Port 84h,
|
||
85h, or 86h (depending on whether counter 0, 1, or 2 should be initialized).
|
||
The four possible Read/Write modes are:
|
||
0 = Latch Counter for Reading 2 = Load high byte
|
||
1 = Load low byte 3 = Load low and high byte
|
||
|
||
Kanji ROM
|
||
---------
|
||
|
||
Port D8h Select Class 1 Kanji Code (lower 6 bits)
|
||
Port D9h Select Class 1 Kanji Code (upper 6 bits)
|
||
Port D9h Read Data for Class 1 Kanji Code (32 bytes)
|
||
Port DAh Select Class 2 Kanji Code (lower 6 bits)
|
||
Port DBh Select Class 2 Kanji Code (upper 6 bits)
|
||
Port DBh Read Data for Class 2 Kanji Code (32 bytes)
|
||
|
||
Class 1 and Class 2 Kanji Characters
|
||
Class 1 and Class 2 Kanji are two japanese character sets. Note that not all
|
||
MSX computers support both Class 1 and Class 2. Most european MSX computers
|
||
probably don't include either one at all.
|
||
The Class 1 character set also contains various european, greek, and symbolic
|
||
characters. Note that different Kanji ROM versions exist, the characters may
|
||
have slightly different appearances (and in some cases even different
|
||
meanings).
|
||
|
||
Reading Kanji Codes
|
||
For Class 1 codes use Port D8h-D9h, for Class 2 codes use Port DAh-DBh.
|
||
Output the lower and upper bits of the Kanji Code (ie. the desired character
|
||
number), then read 32 bytes from the respective Kanji Data port. These 32
|
||
bytes define a 16x16 pixel bitmap which is split into 4 tiles of 8x8 pixels
|
||
each (first tile: upper left, second: upper right, third: lower left, and
|
||
fourth: lower right).
|
||
|
||
Special I/O Registers
|
||
---------------------
|
||
|
||
Port F5 System Control (Write Only)
|
||
Port F7 A/V Control (Read/Write)
|
||
|
||
Port F5h, System Control (Write only)
|
||
Setting bits to "1" enables available I/O devices.
|
||
Bit Expl.
|
||
0 Kanji ROM Class 1
|
||
1 Kanji ROM Class 2 (?)
|
||
2 MSX-AUDIO
|
||
3 Superimpose
|
||
4 MSX interface
|
||
5 RS-232C
|
||
6 Lightpen
|
||
7 CLOCK-IC (only on MSX2)
|
||
Bits to void the conflict between internal I/O devices or those connected by
|
||
cartridge. The bits can disable the internal devices. When BIOS is
|
||
initialised, internal devices are valid if no external devices are connected.
|
||
Applications may not write to or read from here.
|
||
|
||
Port F7h, Audio/Video Control (A/V Control)
|
||
Bit R/W Expl.
|
||
0 W Audio R (mixing ON)
|
||
1 W Audio L (mixing OFF)
|
||
2 W Select video input (21p RGB)
|
||
3 -R- Detect video input (no input)
|
||
4 W AV control (TV)
|
||
5 W Ym control (TV)
|
||
6 W Inverse of bit 4 of VDP register 9
|
||
7 W Inverse of bit 5 of VDP register 9
|
||
|
||
Z80 CPU Specifications
|
||
----------------------
|
||
|
||
--> Z80 Usage in MSX Models
|
||
--> Z80 Register Set
|
||
--> Z80 Flags
|
||
--> Z80 Instruction Format
|
||
--> Z80 8bit Load Commands
|
||
--> Z80 16bit Load Commands
|
||
--> Z80 Blocktransfer- and Searchcommands
|
||
--> Z80 8bit Arithmetic/Logical Commands
|
||
--> Z80 16bit Arithmetic Commands
|
||
--> Z80 Rotate and Shift Commands
|
||
--> Z80 Singlebit Operations and CPU-Control Commands
|
||
--> Z80 Jumpcommands
|
||
--> Z80 I/O Commands
|
||
--> Z80 Interrupts
|
||
--> Z80 Meaningless and Duplicated Opcodes
|
||
--> Z80 Garbage in Flag Register
|
||
--> Z80 Compatibility
|
||
|
||
Z80 Usage in MSX Models
|
||
-----------------------
|
||
|
||
Opcode Timings
|
||
Both MSX 1 and MSX 2 are using a Z80A CPU, operating at 3.579545MHz.
|
||
The execution time for each instruction is the number of clock cycles
|
||
(specified in the instruction lists below) - plus the number of refresh cycles
|
||
for that instruction.
|
||
|
||
One refresh cycle is performed for each normal instruction. A total of two
|
||
refresh cycles is performed for all instructions which include the following
|
||
prefix byte(s): CB, ED, DD, FD, DDCB, or FDCB.
|
||
For example, a NOP instruction counts 4 cycles plus 1 refresh cycle, resulting
|
||
in a execution time of 5 cycles, ie. 5/3579545 seconds.
|
||
|
||
Interrupts
|
||
Interrupts are supplied by the Video Display Controller (VDP) only. Note that
|
||
these interrupts must be manually acknowledged.
|
||
Non-maskable interrupts (NMIs) are not used. In Interrupt modes IM 0 and IM 2
|
||
an undefined parameter byte is supplied on the databus.
|
||
|
||
Z80 Register Set
|
||
----------------
|
||
|
||
Register Summary
|
||
16bit Hi Lo Name/Function
|
||
---------------------------------------
|
||
AF A - Accumulator & Flags
|
||
BC B C BC
|
||
DE D E DE
|
||
HL H L HL
|
||
AF' - - Second AF
|
||
BC' - - Second BC
|
||
DE' - - Second DE
|
||
HL' - - Second HL
|
||
IX IXH IXL Index register 1
|
||
IY IYH IYL Index register 2
|
||
SP - - Stack Pointer
|
||
PC - - Program Counter/Pointer
|
||
- I R Interrupt & Refresh
|
||
|
||
Normal 8bit and 16bit Registers
|
||
The Accumulator (A) is the allround register for 8bit operations. Registers B,
|
||
C, D, E, H, L are normal 8bit registers, which can be also accessed as 16bit
|
||
register pairs BC, DE, HL.
|
||
The HL register pair is used as allround register for 16bit operations. B and
|
||
BC are sometimes used as counters. DE is used as DEstination pointer in block
|
||
transfer commands.
|
||
|
||
Second Register Set
|
||
The Z80 includes a second register set (AF',BC',DE',HL') these registers
|
||
cannot be accessed directly, but can be exchanged with the normal registers by
|
||
using the EX AF,AF and EXX instructions.
|
||
|
||
Refresh Register
|
||
The lower 7 bits of the Refresh Register (R) are incremented with every
|
||
instruction. Instructions with at least one prefix-byte (CB,DD,ED,FD, or
|
||
DDCB,FDCB) will increment the register twice. Bit 7 can be used by programmer
|
||
to store data. Permanent writing to this register will suppress memory refresh
|
||
signals, causing Dynamic RAM to lose data.
|
||
|
||
Interrupt Register
|
||
The Interrupt Register (I) is used in interrupt mode 2 only (see command "im
|
||
2"). In other modes it can be used as simple 8bit data register.
|
||
|
||
IX and IY Registers
|
||
IX and IY are able to manage almost all the things that HL is able to do. When
|
||
used as memory pointers they are additionally including a signed index byte
|
||
(IX+d). The disadvantage is that the opcodes occupy more memory bytes, and
|
||
that they are less fast than HL-instructions.
|
||
|
||
Undocumented 8bit Registers
|
||
IXH, IXL, IYH, IYL are undocumented 8bit registers which can be used to access
|
||
high and low bytes of the IX and IY registers (much like H and L for HL). Even
|
||
though these registers do not officially exist, they seem to be available in
|
||
all Z80 CPUs, and are quite commonly used by various software.
|
||
|
||
Z80 Flags
|
||
---------
|
||
|
||
Flag Summary
|
||
The Flags are located in the lower eight bits of the AF register pair.
|
||
Bit Name Set Clr Expl.
|
||
0 C C NC Carry Flag
|
||
1 N - - Add/Sub-Flag (BCD)
|
||
2 P/V PE PO Parity/Overflow-Flag
|
||
3 - - - Undocumented
|
||
4 H - - Half-Carry Flag (BCD)
|
||
5 - - - Undocumented
|
||
6 Z Z NZ Zero-Flag
|
||
7 S M P Sign-Flag
|
||
|
||
Carry Flag (C)
|
||
This flag signalizes if the result of an arithmetic operation exceeded the
|
||
maximum range of 8 or 16 bits, ie. the flag is set if the result was less than
|
||
Zero, or greater than 255 (8bit) or 65535 (16bit). After rotate/shift
|
||
operations the bit that has been 'shifted out' is stored in the carry flag.
|
||
|
||
Zero Flag (Z)
|
||
Signalizes if the result of an operation has been zero (Z) or not zero (NZ).
|
||
Note that the flag is set (1) if the result was zero (0).
|
||
|
||
Sign Flag (S)
|
||
Signalizes if the result of an operation is negative (M) or positive (P), the
|
||
sign flag is just a copy of the most significant bit of the result.
|
||
|
||
Parity/Overflow Flag (P/V)
|
||
This flag is used as Parity Flag, or as Overflow Flag, or for other purposes,
|
||
depending on the instruction.
|
||
Parity: Bit7 XOR Bit6 XOR Bit5 ... XOR Bit0 XOR 1.
|
||
8bit Overflow: Indicates if the result was greater/less than +127/-128.
|
||
HL Overflow: Indicates if the result was greater/less than +32767/-32768.
|
||
After LD A,I or LD A,R: Contains current state of IFF2.
|
||
After LDI,LDD,CPI,CPD,CPIR,CPDR: Set if BC<>0 at end of operation.
|
||
|
||
BCD Flags (H,N)
|
||
These bits are solely supposed to be used by the DAA instruction. The N flag
|
||
signalizes if the previous operation has be an addition or substraction. The H
|
||
flag indicates if the lower 4 bits exceeded the range from 0-0Fh. (For 16bit
|
||
instructions: H indicates if the lower 12 bits exceeded the range from
|
||
0-0FFFh.)
|
||
After adding/subtracting two 8bit BCD values (0-99h) the DAA instruction can
|
||
be used to convert the hexadecimal result in the A register (0-FFh) back to
|
||
BCD format (0-99h). Note that DAA also requires the carry flag to be set
|
||
correctly, and thus should not be used after INC A or DEC A.
|
||
|
||
Undocumented Flags (Bit 3,5)
|
||
The content of these undocumented bits is by garbage by all instructions that
|
||
affect one or more of the normal flags (for more info read the chapter Garbage
|
||
in Flag Register), the only way to read out these flags would be to copy the
|
||
flags register onto the stack by using the PUSH AF instruction.
|
||
However, the existence of these bits makes the AF register a full 16bit
|
||
register, so that for example the code sequence PUSH DE, POP AF, PUSH AF, POP
|
||
HL would set HL=DE with all 16bits intact.
|
||
|
||
Z80 Instruction Format
|
||
----------------------
|
||
|
||
Commands and Parameters
|
||
Each instruction consists of a command, and optionally one or two parameters.
|
||
Usually the leftmost parameter is modified by the operation when two
|
||
parameters are specified.
|
||
|
||
Parameter Placeholders
|
||
The following placeholders are used in the following chapters:
|
||
r 8bit register A,B,C,D,E,H,L
|
||
rr 16bit register BC, DE, HL/IX/IY, AF/SP (as described)
|
||
i 8bit register A,B,C,D,E,IXH/IYH,IXL/IYL
|
||
ii 16bit register IX,IY
|
||
n 8bit immediate 00-FFh (unless described else)
|
||
nn 16bit immediate 0000-FFFFh
|
||
d 8bit signed offset -128..+127
|
||
f flag condition nz,z,nc,c AND/OR po,pe,p,m (as described)
|
||
(..) 16bit pointer to byte/word in memory
|
||
|
||
Opcode Bytes
|
||
Each command (including parameters) consists of 1-4 bytes. The respective
|
||
bytes are described in the following chapters. In some cases the register
|
||
number or other parameters are encoded into some bits of the opcode, in that
|
||
case the opcode is specified as "xx". Opcode prefix bytes "DD" (IX) and "FD"
|
||
(IY) are abbreviated as "pD".
|
||
|
||
Clock Cycles
|
||
The clock cycle values in the following chapters specify the execution time of
|
||
the instruction. For example, an 8-cycle instruction would take 2 microseconds
|
||
on a CPU which is operated at 4MHz (8/4 ms). For conditional instructions two
|
||
values are specified, for example, 17;10 means 17 cycles if condition true,
|
||
and 10 cycles if false.
|
||
Note that in case that WAIT signals are sent to the CPU by the hardware then
|
||
the execution may take longer.
|
||
|
||
Affected Flags
|
||
The instruction tables below are including a six character wide field for the
|
||
six flags: Sign, Zero, Halfcarry, Parity/Overflow, N-Flag, and Carry (in that
|
||
order). The meaning of the separate characters is:
|
||
s Indicates Signed result
|
||
z Indicates Zero
|
||
h Indicates Halfcarry
|
||
o Indicates Overflow
|
||
p Indicates Parity
|
||
c Indicates Carry
|
||
- Flag is not affected
|
||
0 Flag is cleared
|
||
1 Flag is set
|
||
x Flag is destroyed (unspecified)
|
||
i State of IFF2
|
||
e Indicates BC<>0 for LDX(R) and CPX(R), or B=0 for INX(R) and OUTX(R)
|
||
|
||
Z80 8bit Load Commands
|
||
----------------------
|
||
Instruction Opcode Cycles Flags Notes
|
||
ld r,r xx 4 ------ r=r
|
||
ld i,i pD xx 8 ------ i=i
|
||
ld r,n xx nn 7 ------ r=n
|
||
ld i,n pD xx nn 11 ------ i=n
|
||
ld r,(HL) xx 7 ------ r=(HL)
|
||
ld r,(ii+d) pD xx dd 19 ------ r=(ii+d)
|
||
ld (HL),r 7x 7 ------ (HL)=r
|
||
ld (ii+d),r pD 7x dd 19 ------
|
||
ld (HL),n 36 nn 10 ------
|
||
ld (ii+d),n pD 36 dd nn 19 ------
|
||
ld A,(BC) 0A 7 ------
|
||
ld A,(DE) 1A 7 ------
|
||
ld A,(nn) 3A nn nn 13 ------
|
||
ld (BC),A 02 7 ------
|
||
ld (DE),A 12 7 ------
|
||
ld (nn),A 32 nn nn 13 ------
|
||
ld A,I ED 57 9 sz0i0- A=I ;Interrupt Register
|
||
ld A,R ED 5F 9 sz0i0- A=R ;Refresh Register
|
||
ld I,A ED 47 9 ------
|
||
ld R,A ED 4F 9 ------
|
||
|
||
Z80 16bit Load Commands
|
||
-----------------------
|
||
Instruction Opcode Cycles Flags Notes
|
||
ld rr,nn x1 nn nn 10 ------ rr=nn ;rr may be BC,DE,HL or SP
|
||
ld ii,nn pD 21 nn nn 13 ------ ii=nn
|
||
ld HL,(nn) 2A nn nn 16 ------ HL=(nn)
|
||
ld ii,(nn) pD 2A nn nn 20 ------ ii=(nn)
|
||
ld rr,(nn) ED xB nn nn 20 ------ rr=(nn) ;rr may be BC,DE,HL or SP
|
||
ld (nn),HL 22 nn nn 16 ------ (nn)=HL
|
||
ld (nn),ii pD 22 nn nn 20 ------ (nn)=ii
|
||
ld (nn),rr ED x3 nn nn 20 ------ (nn)=rr ;rr may be BC,DE,HL or SP
|
||
ld SP,HL F9 6 ------ SP=HL
|
||
ld SP,ii pD F9 10 ------ SP=ii
|
||
push rr x5 11 ------ SP=SP-2, (SP)=rr ;rr may be BC,DE,HL,AF
|
||
push ii pD E5 15 ------ SP=SP-2, (SP)=ii
|
||
pop rr x1 10 (-AF-) rr=(SP), SP=SP+2 ;rr may be BC,DE,HL,AF
|
||
pop ii pD E1 14 ------ ii=(SP), SP=SP+2
|
||
ex DE,HL EB 4 ------ exchange DE <--> HL
|
||
ex AF,AF 08 4 xxxxxx exchange AF <--> AF'
|
||
exx D9 4 ------ exchange BC,DE,HL <--> BC',DE',HL'
|
||
ex (SP),HL E3 19 ------ exchange (SP) <--> HL
|
||
ex (SP),ii pD E3 23 ------ exchange (SP) <--> ii
|
||
|
||
Z80 Blocktransfer- and Searchcommands
|
||
-------------------------------------
|
||
Instruction Opcode Cycles Flags Notes
|
||
ldi ED A0 16 --0e0- (DE)=(HL), HL=HL+1, DE=DE+1, BC=BC-1
|
||
ldd ED A8 16 --0e0- (DE)=(HL), HL=HL-1, DE=DE-1, BC=BC-1
|
||
cpi ED A1 16 szhe1- compare A-(HL), HL=HL+1, DE=DE+1,
|
||
BC=BC-1
|
||
cpd ED A9 16 szhe1- compare A-(HL), HL=HL-1, DE=DE-1,
|
||
BC=BC-1
|
||
ldir ED B0 bc*21-5 --0?0- ldi-repeat until BC=0
|
||
lddr ED B8 bc*21-5 --0?0- ldd-repeat until BC=0
|
||
cpir ED B1 x*21-5 szhe1- cpi-repeat until BC=0 or compare fits
|
||
cpdr ED B9 x*21-5 szhe1- cpd-repeat until BC=0 or compare fits
|
||
|
||
Z80 8bit Arithmetic/Logical Commands
|
||
------------------------------------
|
||
Instruction Opcode Cycles Flags Notes
|
||
daa 27 4 szxp-x decimal adjust akku
|
||
cpl 2F 4 --1-1- A = A xor FF
|
||
neg ED 44 8 szho1c A = 00-A
|
||
<arit> r xx 4 szhonc see below
|
||
<arit> i pD xx 8 szhonc see below, UNDOCUMENTED
|
||
<arit> n xx nn 7 szhonc see below
|
||
<arit> (HL) xx 7 szhonc see below
|
||
<arit> (ii+d) pD xx dd 19 szhonc see below
|
||
<cnt> r xx 4 szhon- see below
|
||
<cnt> i pD xx 8 szhon- see below, UNDOCUMENTED
|
||
<cnt> (HL) xx 11 szhon- see below
|
||
<cnt> (ii+d) pD xx dd 23 szhon- see below
|
||
<logi> r xx 4 szhp00 see below
|
||
<logi> i pD xx 8 szhp00 see below, UNDOCUMENTED
|
||
<logi> n xx nn 7 szhp00 see below
|
||
<logi> (HL) xx 7 szhp00 see below
|
||
<logi> (ii+d) pD xx dd 19 szhp00 see below
|
||
Arithmetic <arit> commands:
|
||
add A,op see above 4-19 szho0c A=A+op
|
||
adc A,op see above 4-19 szho0c A=A+op+cy
|
||
sub op see above 4-19 szho1c A=A-op
|
||
sbc A,op see above 4-19 szho1c A=A-op-cy
|
||
cp op see above 4-19 szho1c compare, ie. VOID=A-op
|
||
Increment/Decrement <cnt> commands:
|
||
inc op see above 4-23 szho0- op=op+1
|
||
dec op see above 4-23 szho1- op=op-1
|
||
Logical <logi> commands:
|
||
and op see above 4-19 sz1p00 A=A & op
|
||
xor op see above 4-19 sz0p00 A=A XOR op
|
||
or op see above 4-19 sz0p00 A=A | op
|
||
|
||
Z80 16bit Arithmetic Commands
|
||
-----------------------------
|
||
Instruction Opcode Cycles Flags Notes
|
||
add HL,rr x9 11 --h-0c HL = HL+rr ;rr may be BC,DE,HL,SP
|
||
add ii,rr pD x9 15 --h-0c ii = ii+rr ;rr may be BC,DE,ii,SP (!)
|
||
adc HL,rr ED xA 15 szho0c HL = HL+rr+cy ;rr may be BC,DE,HL,SP
|
||
sbc HL,rr ED x2 15 szho1c HL = HL-rr-cy ;rr may be BC,DE,HL,SP
|
||
inc rr x3 6 ------ rr = rr+1 ;rr may be BC,DE,HL,SP
|
||
inc ii pD 23 10 ------ ii = ii+1
|
||
dec rr xB 6 ------ rr = rr-1 ;rr may be BC,DE,HL,SP
|
||
dec ii pD 2B 10 ------ ii = ii-1
|
||
|
||
Z80 Rotate and Shift Commands
|
||
-----------------------------
|
||
Instruction Opcode Cycles Flags Notes
|
||
rlca 07 4 --0-0c rotate akku left
|
||
rla 17 4 --0-0c rotate akku left through carry
|
||
rrca 0F 4 --0-0c rotate akku right
|
||
rra 1F 4 --0-0c rotate akku right through carry
|
||
rld ED 6F 18 sz0p0- rotate left low digit of A through (HL)
|
||
rrd ED 67 18 sz0p0- rotate right low digit of A through (HL)
|
||
<cmd> r CB xx 8 sz0p0c see below
|
||
<cmd> (HL) CB xx 15 sz0p0c see below
|
||
<cmd> (ii+d) pD CB dd xx 23 sz0p0c see below
|
||
<cmd> r,(ii+d) pD CB dd xx 23 sz0p0c see below, UNDOCUMENTED modify and load
|
||
Whereas <cmd> may be:
|
||
rlc rotate left
|
||
rl rotate left through carry
|
||
rrc rotate right
|
||
rr rotate right through carry
|
||
sla shift left arithmetic (b0=0)
|
||
sll UNDOCUMENTED shift left (b0=1)
|
||
sra shift right arithmetic (b7=b7)
|
||
srl shift right logical (b7=0)
|
||
|
||
Z80 Singlebit Operations and CPU-Control Commands
|
||
-------------------------------------------------
|
||
Instruction Opcode Cycles Flags Notes
|
||
bit n,r CB xx 8 xz1x0- test bit n ;n=0..7
|
||
bit n,(HL) CB xx 12 xz1x0-
|
||
bit n,(ii+d) pD CB dd xx 20 xz1x0-
|
||
set n,r CB xx 8 ------ set bit n ;n=0..7
|
||
set n,(HL) CB xx 15 ------
|
||
set n,(ii+d) pD CB dd xx 23 ------
|
||
set r,n,(ii+d) pD CB dd xx 23 ------ UNDOCUMENTED set n,(ii+d) and ld
|
||
r,(ii+d)
|
||
res n,r CB xx 8 ------ reset bit n ;n=0..7
|
||
res n,(HL) CB xx 15 ------
|
||
res n,(ii+d) pD CB dd xx 23 ------
|
||
res r,n,(ii+d) pD CB dd xx 23 ------ UNDOCUMENTED res n,(ii+d) and ld
|
||
r,(ii+d)
|
||
ccf 3F 4 --h-0c h=cy, cy=cy xor 1
|
||
scf 37 4 --0-01 cy=1
|
||
nop 00 4 ------ no operation
|
||
halt 76 4 ------ repeat until interrupt occurs
|
||
di F3 4 ------ iff=0 ;disable interrupts
|
||
ei FB 4 ------ iff=1 ;enable interrupts
|
||
im 0 ED 46 8 ------ read opcode from databus on interrupt
|
||
im 1 ED 56 8 ------ execute call 0038h on interrupt
|
||
im 2 ED 5E 8 ------ execute call (i*100h+databus) on int.
|
||
|
||
Z80 Jumpcommands
|
||
----------------
|
||
Instruction Opcode Cycles Flags Notes
|
||
jp nn C3 nn nn 10 ------ jump to nn, ie. PC=nn
|
||
jp HL E9 4 ------ jump to HL, ie. PC=HL
|
||
jp ii pD E9 8 ------ jump to ii, ie. PC=ii
|
||
jp f,nn xx nn nn 10;10 ------ jump to nn if nz,z,nc,c,po,pe,p,m
|
||
jr nn 18 dd 12 ------ relative jump to nn, ie. PC=PC+d
|
||
jr f,nn xx dd 12;7 ------ relative jump to nn if nz,z,nc,c
|
||
djnz nn 10 dd 13;8 ------ B=B-1 and relative jump to nn if B<>0
|
||
call nn CD nn nn 17 ------ call nn ie. SP=SP-2, (SP)=PC, PC=nn
|
||
call f,nn xx nn nn 17;10 ------ call nn if nz,z,nc,c,po,pe,p,m
|
||
ret C9 10 ------ pop PC ie. PC=(SP), SP=SP+2
|
||
ret f xx 11;5 ------ pop PC if nz,z,nc,c,po,pe,p,m
|
||
reti ED 4D 14 ------ pop PC, IFF2=IFF1 (ret from INT)
|
||
retn ED 45 14 ------ pop PC, IFF2=IFF1 (ret from NMI)
|
||
rst n xx 11 ------ call n ;n=00,08,10,18,20,28,30,38
|
||
|
||
Z80 I/O Commands
|
||
----------------
|
||
Instruction Opcode Cycles Flags Notes
|
||
in A,(n) DB nn 11 ------ A=PORT(A*100h+n)
|
||
in r,(C) ED xx 12 sz0p0- r=PORT(BC)
|
||
in (C) ED 70 12 sz0p0- **undoc/illegal** VOID=PORT(BC)
|
||
out (n),A D3 nn 11 ------ PORT(A*100h+n)=A
|
||
out (C),r ED xx 12 ------ PORT(BC)=r
|
||
out (C),0 ED 71 12 ------ **undoc/illegal** PORT(BC)=00
|
||
ini ED A2 16 xexxxx MEM(HL)=PORT(BC), HL=HL+1, B=B-1
|
||
ind ED AA 16 xexxxx MEM(HL)=PORT(BC), HL=HL-1, B=B-1
|
||
outi ED A3 16 xexxxx B=B-1, PORT(BC)=MEM(HL), HL=HL+1
|
||
outd ED AB 16 xexxxx B=B-1, PORT(BC)=MEM(HL), HL=HL-1
|
||
inir ED B2 b*21-5 x1xxxx same than ini, repeat until b=0
|
||
indr ED BA b*21-5 x1xxxx same than ind, repeat until b=0
|
||
otir ED B3 b*21-5 x1xxxx same than outi, repeat until b=0
|
||
otdr ED BB b*21-5 x1xxxx same than outd, repeat until b=0
|
||
|
||
Z80 Interrupts
|
||
--------------
|
||
|
||
Lack of Information
|
||
Z80 interrupts are a mysterium, the official Z80 documentation basically
|
||
denied the existence of interrupts in general. However, when describing
|
||
opcodes such like IM 0, EI, and RETI the author couldn't fully avoid to
|
||
mention the possibility that such a thing like interrupts might eventually
|
||
exist by suggesting to refer to somewhat called an "application script about
|
||
interrupt behaviour of Z80 systems".
|
||
|
||
In case that this document really exists, then it is probably been horribly
|
||
expensive, made available to authorized developers only, and not available
|
||
nowadays anymore. The content of this document might or might not confirm the
|
||
existence of interrupts, and/or explain other details?
|
||
|
||
Judging from the fragments of information the leaked out in the Z80 docs, the
|
||
CPU supports non-maskable interrupts (NMI) and maskable interrupts (INT). MSX
|
||
and CPC homecomputers aren't using NMIs, so information below is reverse
|
||
engineered guesswork for systems that use maskable interrupts only.
|
||
|
||
Interrupt Flip-Flop (IFF1,IFF2)
|
||
These internal flags are used to enable/disable interrupts, in a raw INT based
|
||
system which isn't using NMIs, it appears to be safe to treat these flags as a
|
||
single IFF flag, instead separate IFF1 and IFF2.
|
||
|
||
Interrupts can be enabled by the EI instruction (IFF=1) only, whereas the new
|
||
IFF state isn't applied until the next instruction has completed (this ensures
|
||
that an interrupt handler which is using the sequence "EI, RET" may return to
|
||
the main program before the next interrupt is executed).
|
||
Interrupts can be disabled by the DI instruction (IFF=0), and are additionally
|
||
automatically each time when an interrupt is executed.
|
||
|
||
Interrupt Execution
|
||
An interrupt is executed when an interrupt is requested by the hardware, and
|
||
IFF is set. Whenever both conditions are true, the interrupt is executed after
|
||
the completion of the current opcode.
|
||
Note that repeated block commands (such like LDIR) can be interrupted also,
|
||
the interrupt return address on the stack then points to the interrupted
|
||
opcode, so that the instruction may continue as normal once the interrupt
|
||
handler returns.
|
||
|
||
Interrupt Modes (IM 0,1,2)
|
||
The Z80 supports three interrupts modes which can be selected by IM 0, IM 1,
|
||
and IM 2 instructions. The table below describes the respective operation and
|
||
execution time upon interrupt execution in each mode.
|
||
Mode Cycles Refresh Operation
|
||
0 1+var 0+var IFF=0, read and execute opcode from databus
|
||
1 12 1 IFF=0, CALL 0038h
|
||
2 18 1 IFF=0, CALL (I*100h+databus)
|
||
Mode 0 requires an opcode to be output to the databus by external hardware, in
|
||
case that no byte is output, and provided that the 'empty' databus is free of
|
||
garbage, then the CPU might tend to read a value of FFh (opcode RST 38h) - the
|
||
clock cycles, refresh cycles, and executed operation are then fully identical
|
||
as in Mode 1.
|
||
Mode 1 interrupts always perform a CALL 0038h operation. The downside is that
|
||
many systems may have ROM located at this address, making it impossible to
|
||
hook the interrupt handler directly.
|
||
|
||
Mode 2 calls to a 16bit address which is read from a table in memory, the
|
||
table pointer is calculated from the "I" register (initialized by LD I,A
|
||
instruction) multiplied by 100h, plus an index byte which is read from the
|
||
databus. The following trick may be used to gain stable results in Mode 2 even
|
||
if no index byte is supplied on the databus: For example, set I=40h the origin
|
||
of the table will be then at 4000h on memory. Now fill the entire area from
|
||
4000h to 4100h (101h bytes, including 4100h) by the value 41h. The CPU will
|
||
then perform a CALL 4141h upon interrupt execution - regardless of whether the
|
||
randomized index byte is a even or odd number.
|
||
|
||
RETI and RETN
|
||
These instructions are somewhat supposed to return from maskable and
|
||
non-maskable interrupts. In a raw INT based system which isn't using NMIs they
|
||
appear to behave 100% identical to normal RET instructions.
|
||
|
||
Z80 Meaningless and Duplicated Opcodes
|
||
--------------------------------------
|
||
|
||
Mirrored Instructions
|
||
NEG (ED44) is mirrored to ED4C,54,5C,64,6C,74,7C.
|
||
RETN (ED45) is mirrored to ED55,65,75.
|
||
RETI (ED4D) is mirrored to ED5D,6D,7D.
|
||
|
||
Mirrored IM Instructions
|
||
IM 0,X,1,2 (ED46,4E,56,5E) are mirrored to ED66,6E,76,7E.
|
||
Whereas IM X is an undocumented mirrored instruction itself which appears to
|
||
be identical to either IM 0 or IM 1 instruction (?).
|
||
|
||
Duplicated LD HL Instructions
|
||
LD (nn),HL (opcode 22NNNN) is mirrored to ED63NNNN.
|
||
LD HL,(nn) (opcode 2ANNNN) is mirrored to ED6BNNNN.
|
||
Unlike the other instructions in this chapter, these two opcodes are
|
||
officially documented. The clock/refresh cycles for the mirrored instructions
|
||
are then 20/2 instead of 16/1 as for the native 8080 instructions.
|
||
|
||
Mirrored BIT N,(ii+d) Instructions
|
||
Unlike as for RES and SET, the BIT instruction does not support a third
|
||
operand, ie. DD or FD prefixes cannot be used on a BIT N,r instruction in
|
||
order to produce a BIT r,N,(ii+d) instruction. When attempting this, the 'r'
|
||
operand is ignored, and the resulting instruction is identical to BIT
|
||
N,(ii+d).
|
||
Except that, not tested yet, maybe undocumented flags are then read from 'r'
|
||
instead of from ii+d(?).
|
||
|
||
Non-Functional Opcodes
|
||
The following opcodes behave much like the NOP instruction.
|
||
ED00-3F, ED77, ED7F, ED80-9F, EDA4-A7, EDAC-AF, EDB4-B7, EDBC-BF, EDC0-FF.
|
||
The execution time for these opcodes is 8 clock cycles, 2 refresh cycles.
|
||
Note that some of these opcodes appear to be used for additional instructions
|
||
by the R800 CPU in newer turbo R models.
|
||
|
||
Ignored DD and FD Prefixes
|
||
In some cases, DD-prefixes (IX) and FD-prefixes (IY) may be ignored by the
|
||
CPU. This happens when using one (or more) of the above prefixes prior to
|
||
instructions that already contain an ED, DD, or FD prefix, or prior to any
|
||
instructions that do not support IX, IY, IXL, IXH, IYL, IYH operands. In such
|
||
cases, 4 clock cycles and 1 refresh cycle are counted for each ignored prefix
|
||
byte.
|
||
|
||
Z80 Garbage in Flag Register
|
||
----------------------------
|
||
|
||
Nocash Z80-flags description
|
||
This chapter describes the undocumented Z80 flags (bit 3 and 5 of the Flags
|
||
Register), these flags are affected by ALL instructions that modify one or
|
||
more of the normal flags - all OTHER instructions do NOT affect the
|
||
undocumented flags.
|
||
|
||
For some instructions, the content of some flags has been officially
|
||
documented as 'destroyed', indicating that the flags contain garbage, the
|
||
exact garbage calculation for these instructions will be described here also.
|
||
|
||
All information below just for curiosity. Keep in mind that Z80 compatible
|
||
CPUs (or emulators) may not supply identical results, so that it wouldn't be a
|
||
good idea to use these flags in any programs (not that they could be very
|
||
useful anyways).
|
||
|
||
Normal Behaviour for Undocumented Flags
|
||
In most cases, undocumented flags are copied from the Bit 3 and Bit 5 of the
|
||
result byte. That is "A AND 28h" for:
|
||
RLD; CPL; RLCA; RLA; LD A,I; ADD OP; ADC OP; XOR OP; AND OP;
|
||
RRD; NEG; RRCA; RRA; LD A,R; SUB OP; SBC OP; OR OP ; DAA.
|
||
When other operands than A may be modified, "OP AND 28h" for:
|
||
RLC OP; RL OP; SLA OP; SLL OP; INC OP; IN OP,(C);
|
||
RRC OP; RR OP; SRA OP; SRL OP; DEC OP
|
||
For 16bit instructions flags are calculated as "RR AND 2800h":
|
||
ADD RR,XX; ADC RR,XX; SBC RR,XX.
|
||
|
||
Slightly Special Undocumented Flags
|
||
For 'CP OP' flags are calculated as "OP AND 28h", that is the unmodified
|
||
operand, and NOT the internally calculated result of the comparision.
|
||
For 'SCF' and 'CCF' flags are calculated as "(A OR F) AND 28h", ie. the flags
|
||
remain set if they have been set before.
|
||
For 'BIT N,R' flags are calculated as "OP AND 28h", additionally the P-Flag is
|
||
set to the same value than the Z-Flag (ie. the Parity of "OP AND MASK"), and
|
||
the S-flag is set to "OP AND MASK AND 80h".
|
||
|
||
Fatal MEMPTR Undocumented Flags
|
||
For 'BIT N,(HL)' the P- and S-flags are set as for BIT N,R, but the
|
||
undocumented flags are calculated as "MEMPTR AND 2800h", for more info about
|
||
MEMPTR read on below.
|
||
The same applies to 'BIT N,(ii+d)', but the result is less unpredictable
|
||
because the instruction sets MEMPTR=ii+d, so that undocumented flags are
|
||
"<ii+d> AND 2800h".
|
||
|
||
Memory Block Command Undocumented Flags
|
||
For LDI, LDD, LDIR, LDDR, undocumented flags are "((A+DATA) AND 08h) +
|
||
((A+DATA) AND 02h)*10h".
|
||
For CPI, CPD, CPIR, CPDR, undocumented flags are "((A-DATA-FLG_H) AND 08h) +
|
||
((A-DATA-FLG_H) AND 02h)*10h", whereas the CPU first calculates A-DATA, and
|
||
then internally subtracts the resulting H-flag from the result.
|
||
|
||
Chaotic I/O Block Command Flags
|
||
The INI, IND, INIR, INDR, OUTI, OUTD, OTIR, OTDR instructions are doing a lot
|
||
of obscure things, to simplify the description a placeholder called DUMMY is
|
||
used in the formulas.
|
||
DUMMY = "REG_C+DATA+1" ;for INI/INIR
|
||
DUMMY = "REG_C+DATA-1" ;for IND/INDR
|
||
DUMMY = "REG_L+DATA" ;for OUTI,OUTD,OTIR,OTDR
|
||
FLG_C = Carry of above "DUMMY" calculation
|
||
FLG_H = Carry of above "DUMMY" calculation (same as FLG_C)
|
||
FLG_N = Sign of "DATA"
|
||
FLG_P = Parity of "REG_B XOR (DUMMY AND 07h)"
|
||
FLG_S = Sign of "REG_B"
|
||
UNDOC = Bit3,5 of "REG_B AND 28h"
|
||
The above registers L and B are meant to contain the new values which are
|
||
already incremented/decremented by the instruction.
|
||
Note that the official docs mis-described the N-Flag as set, and the C-Flag as
|
||
not affected.
|
||
|
||
DAA Flags
|
||
Addition (if N was 0):
|
||
FLG_H = (OLD_A AND 0Fh) > 09h
|
||
FLG_C = Carry of result
|
||
Subtraction (if N was 1):
|
||
FLG_H = (NEW_A AND 0Fh) > 09h
|
||
FLG_C = OLD_CARRY OR (OLD_A>99h)
|
||
For both addition and subtraction, N remains unmodified, and S, Z, P contain
|
||
"Sign", Zero, and Parity of result (A). Undocumented flags are set as (A AND
|
||
28h) as normal.
|
||
|
||
Mis-documented Flags
|
||
For all XOR/OR: H=N=C=0, and for all AND: H=1, N=C=0, unlike described else in
|
||
Z80 docs. Also note C,N flag description bug for I/O block commands (see
|
||
above).
|
||
|
||
Internal MEMPTR Register
|
||
This is an internal Z80 register, modified by some instructions, and usually
|
||
completely hidden to the user, except that Bit 11 and Bit 13 can be read out
|
||
at a later time by BIT N,(HL) instructions.
|
||
The following list specifies the resulting content of the MEMPTR register
|
||
caused by the respective instructions.
|
||
Content Instruction
|
||
A*100h LD (xx),A ;xx=BC,DE,nn
|
||
xx+1 LD A,(xx) ;xx=BC,DE,nn
|
||
nn+1 LD (nn),rr; LD rr,(nn) ;rr=BC,DE,HL,IX,IY
|
||
rr EX (SP),rr ;rr=HL,IX,IY (MEMPTR=new value of rr)
|
||
rr+1 ADD/ADC/SBC rr,xx ;rr=HL,IX,IY (MEMPTR=old value of rr+1)
|
||
HL+1 RLD and RRD
|
||
dest JP nn; CALL nn; JR nn ;dest=nn
|
||
dest JP f,nn; CALL f,nn ;regardless of condition true/false
|
||
dest RET; RETI; RETN ;dest=value read from (sp)
|
||
dest RET f; JR f,nn; DJNZ nn ;only if condition=true
|
||
00XX RST n
|
||
adr+1 IN A,(n) ;adr=A*100h+n, memptr=A*100h+n+1
|
||
bc+1 IN r,(BC); OUT (BC),r ;adr=bc
|
||
ii+d All instructions with operand (ii+d)
|
||
Also the following might or might not affect MEMPTR, not tested yet:
|
||
OUT (N),A and block commands LDXX, CPXX, INXX, OUTXX
|
||
and probably interrupts in IM 0, 1, 2
|
||
All other commands do not affect the MEMPTR register - this includes all
|
||
instructions with operand (HL), all PUSH and POP instructions, not executed
|
||
conditionals JR f,d, DJNZ d, RET f (ie. with with condition=false), and the JP
|
||
HL/IX/IY jump instructions.
|
||
|
||
Z80 Compatibility
|
||
-----------------
|
||
|
||
The Z80 CPU is (almost) fully backwards compatible to older 8080 and 8085
|
||
CPUs.
|
||
|
||
Instruction Format
|
||
The Z80 syntax simplifies the chaotic 8080/8085 syntax. For example, Z80 uses
|
||
the command "LD" for all load instructions, 8080/8085 used various different
|
||
commands depending on whether the operands are 8bit registers, 16bit
|
||
registers, memory pointers, and/or an immediates. However, these changes apply
|
||
to the source code only - the generated binary code is identical for both
|
||
CPUs.
|
||
|
||
Parity/Overflow Flag
|
||
The Z80 CPU uses Bit 2 of the flag register as Overflow flag for arithmetic
|
||
instructions, and as Parity flag for other instructions. 8080/8085 CPUs are
|
||
always using this bit as Parity flag for both arithmetic and non-arithmetic
|
||
instructions.
|
||
|
||
Z80 Specific Instructions
|
||
The following instructions are available for Z80 CPUs only, but not for older
|
||
8080/8085 CPUs:
|
||
All CB-prefixed opcodes (most Shift/Rotate, all BIT/SET/RES commands).
|
||
All ED-prefixed opcodes (various instructions, and all block commands).
|
||
All DD/FD-prefixed opcodes (registers IX and IY).
|
||
As well as DJNZ nn; JR nn; JR f,nn; EX AF,AF; and EXX.
|
||
|
||
8085 Specific Instructions
|
||
The 8085 instruction set set includes two specific opcodes in addition to the
|
||
8080 instruction set, used to control 8085-specifc interrupts and SID and SOD
|
||
input/output signals. These opcodes, RIM (20h) and SIM (30h), are not
|
||
supported by Z80 instruction set.
|
||
|
||
Z80 vs Z80A
|
||
Both Z80 and Z80A are including the same instruction set, the only difference
|
||
is the supported clock frequency (Z80 = max 2.5MHz, Z80A = max 4MHz).
|
||
|
||
Different MSX Models
|
||
--------------------
|
||
|
||
MSX computers have been manufactured by almost 40 different companies spread
|
||
all over the world, and most of these companies have assembled their own
|
||
unique hardware combination(s), so that there should be about 100 different
|
||
MSX models.
|
||
All models can be split into four categories: MSX, MSX2, MSX2+, and turbo R.
|
||
Listed below are the most common configurations for each category (not
|
||
including special hardware/firmware expansions that might have been included
|
||
in some models).
|
||
|
||
MSX1
|
||
Z80 CPU (8bit) 3.579545MHz
|
||
PSG Sound: three sound & noise channels
|
||
Keyboard: 72 Keys, CAPs LED, Keyclick Sound
|
||
Video chip: V9918, 40x24 text, 256x192 pix, 16 colors, 32 sprites
|
||
Memory: 32K ROM, 8/16/32/64K RAM, 16K VRAM, Memory Control: Primary Slot
|
||
Connectors: 2 Joysticks, Cassette, RGB and TV, 2 cartridge slots
|
||
|
||
MSX2
|
||
More or less backwards compatible to MSX1
|
||
Video chip: V9938, 80x24 text, 512x212 pix, 256 colors, VRAM DMA operations
|
||
Memory: 48K ROM, 64/128/256K RAM, 64/128K VRAM
|
||
Memory Control: Primary Slot, Secondary Slot, Memory Mapper (for >=128K RAM)
|
||
Built-in disk drive, disk controller, and 16K disk ROM (optional)
|
||
Built-in battery buffered real time clock (optional)
|
||
|
||
MSX2+
|
||
Mostly backwards compatible to MSX2
|
||
Video chip: V9958, horizontal scrolling, max 32768 colors in YJK mode
|
||
FM sound chip -OPLL- YM2413 (additionally to old PSG chip)
|
||
Japanese Kanji ROM charcter set (optional)
|
||
|
||
turbo R
|
||
Don't know. Somewhat using a new Z80 compatible CPU.
|
||
|
||
External Connectors
|
||
-------------------
|
||
|
||
Below information is taken from my Philips MSX1 and MSX2 manuals, but some or
|
||
all connectors might differ for other MSX models.
|
||
|
||
Cartridge Connectors (2)
|
||
1 Out /CS1 ROM addresses 4000-7FFF select signal
|
||
2 Out /CS2 ROM addresses 8000-BFFF select signal
|
||
3 Out /CS12 ROM addresses 4000-BFFF select signal
|
||
4 Out /SLTSL Slot select signal
|
||
5 - Reserved Reserved, don't use
|
||
6 Out /RFSH Refresh cycle signal
|
||
7 In /WAIT CPU's WAIT request signal
|
||
8 In /INT Interrupt request signal to CPU
|
||
9 Out /M1 Signal expressing CPU fetch cycle
|
||
10 In /BUSDIR External data bus buffer direction
|
||
11 Out /IORQ I/O request signal
|
||
12 Out /MERQ Memory request signal
|
||
13 Out /WR Write timing signal
|
||
14 Out /RD Read timing signal
|
||
15 Out /RESET System reset signal
|
||
16 - Reserved Reserved, don't use
|
||
17-32 Out Ax Address bus (A9,15,11,10,7,6,12,8,14,13,1,0,3,2,5,4)
|
||
33-40 I/O Dx Data bus (D1,D0,D3,D2,D5,D4,D7,D6)
|
||
41 - GND Ground
|
||
42 Out CLOCK CPU clock 3.579545MHz
|
||
43 - GND Ground
|
||
44 - SW1 For insertion/removal protect
|
||
45 - +5V +5V power source
|
||
46 - SW2 For insertion/removal protect
|
||
47 - +5V +5V power source
|
||
48 - +12V +12V power source
|
||
49 In SOUNDIN Sound input signal (-5bdm)
|
||
50 - -12V -12V power source
|
||
|
||
Data Recorder Connector
|
||
1-3 GND
|
||
4 Out Data Output (Record)
|
||
5 In Data Input (Play)
|
||
6 Out Remote+
|
||
7 Out Remote-
|
||
8 GND
|
||
|
||
Joystick Connectors (2)
|
||
1 In Up
|
||
2 In Down
|
||
3 In Left
|
||
4 In Right
|
||
5 +5V
|
||
6 I/O Trigger 1
|
||
7 I/O Trigger 2
|
||
8 Out /Select
|
||
9 GND
|
||
|
||
Printer Connector
|
||
1 Out /Strobe
|
||
2-9 Out D0-D7
|
||
10 N/C N/C
|
||
11 In Busy
|
||
12-14 N/C NC
|
||
|
||
Monitor Connector
|
||
Pin PAL-version RGB-version (french only)
|
||
1 - +5V Out Status RGB
|
||
2 - GND - GND
|
||
3 Out Audio Out Blue
|
||
4 Out Luminance Out Luminance
|
||
5 Out Video Out Red
|
||
6 - +12V - +12V
|
||
7 N/C Not Used Out Sound
|
||
8 N/C Not Used Out Green
|
||
|
||
Audio/Video Out (MSX2)
|
||
1 Out Audio Out, right
|
||
2 N/C Audio In, right
|
||
3 Out Audio Out, left
|
||
4 Audio GND
|
||
5 Blue GND
|
||
6 N/C Audio In, left
|
||
7 Out Blue Out
|
||
8 Out Status CVBS
|
||
9 Green GND
|
||
10 N/C NC
|
||
11 Out Green Out
|
||
12 N/C NC
|
||
13 Red GND
|
||
14 GND
|
||
15 Out Red Out
|
||
16 Out Status RGB
|
||
17 CVBS GND
|
||
18 RBG Status GND
|
||
19 Out CVBS Out
|
||
20 N/C CVBS In
|
||
21 Socket GND (Shield)
|
||
|
||
TV Connector
|
||
|
||
Ext. Drive Connector
|
||
4 /In Use Pin 20 /Step
|
||
6 /Drive Select 3 Pin 22 /Write Data
|
||
8 /Index Pin 24 /Write Gate
|
||
10 /Drive Select 0 Pin 26 /Track 00
|
||
12 /Drive Select 1 Pin 28 /Write Protect
|
||
14 /Drive Select 2 Pin 30 /Read Data
|
||
16 /Motor On Pin 32 /(Head Select)
|
||
18 /Direction Pin 34 /Ready
|
||
Pin 1 and 2 are not connected. All other pins are connected to ground (that
|
||
are all pins with odd numbers, in range from 3-33).
|
||
|
||
Power Supply AC 220V (MSX2 with built-in power supply)
|
||
|
||
Power Supply DC (MSX1 with external power supply)
|
||
1 N/C (middle)
|
||
2 GND (upper left)
|
||
3 +12V (lower left)
|
||
4 +5V (lower right)
|
||
5 -12V (upper right)
|
||
|
||
Data Structures and Formats
|
||
---------------------------
|
||
|
||
--> Disk Images
|
||
--> Disk FAT Format
|
||
--> Disk File Formats
|
||
--> Cassette File Formats
|
||
--> ROM Headers
|
||
|
||
Disk Images
|
||
-----------
|
||
|
||
MSX Disk Images (.DSK files) are just a raw copy of the data of all sectors
|
||
from a real disk. The DSK format does not contain any information about the
|
||
physical format of the disk, and thus doesn't support uncommon 'copy
|
||
protected' formats.
|
||
|
||
Usually a disk image contains data for 80 tracks, 9 sectors (sized 200h bytes
|
||
each, and numbered from 01h to 09h). Resulting in an image size of 360Kbytes
|
||
or 720KBytes, depending on whether the disk is single sided, or double sided.
|
||
|
||
However, most MSX disks include basic information in their boot sectors, which
|
||
could be used (if it does exist, and if it is filled out correctly) to
|
||
determine the number of heads, sectors, and tracks of the disk.
|
||
|
||
Disk FAT Format (alias)
|
||
-----------------------
|
||
See chapter Disk FAT Format in FDC description
|
||
|
||
Disk File Formats
|
||
-----------------
|
||
|
||
Binary Files
|
||
Binary files are invented by a 7 bytes header:
|
||
1 byte File type (FEh=binary)
|
||
2 bytes Load Address (Destination Address for Data in RAM)
|
||
2 bytes Last Address (Load Address + Data Length - 1)
|
||
2 bytes Start Address (Used if started as BLOAD"FILE",R)
|
||
Then followed by the actual data.
|
||
|
||
Basic Files
|
||
A basic file is invented by a 1 byte header which contains the file type
|
||
(FFh=basic), the format of the following data is identical as for Basic
|
||
programs which are saved on tapes.
|
||
Note that Basic programs could be also saved (and loaded) in Ascii format.
|
||
|
||
Ascii/Text Files
|
||
Ascii files are saved as raw data without any header. Lines are usually ended
|
||
by CR,LF (0Dh,0Ah) characters. A clean Ascii file should be terminated by an
|
||
EOF (1Ah) character.
|
||
|
||
COM Files
|
||
CP/M and MSXDOS programs are saved as .COM files, these files do not have any
|
||
headers, the load- and startaddress is always 100h. Because of the CP/M
|
||
filesystem, the filesize of CP/M files must be a multiple of 80h.
|
||
|
||
Cassette File Formats
|
||
---------------------
|
||
|
||
Each MSX file consists of two blocks: a header block, and a data block.
|
||
(Except for ascii files, which may have multiple data blocks - but only one
|
||
header block).
|
||
All data is saved without any checksums, readfails could be particulary
|
||
recognized by verifying that each byte has proper Start- and Stopbits. The
|
||
baud rate can be determined by measuring the length of the synchronization
|
||
bits of each block.
|
||
|
||
Format of MSX Header Blocks
|
||
1E00h "1"-bits synchronisation bits
|
||
10 bytes file type (repeated 10 times the same value)
|
||
6 bytes file name (unused entries filled by SPCs)
|
||
The file-type could be binary (D0h), basic (D3h), or ascii (EAh).
|
||
|
||
Format of MSX Basic Data Blocks (Type D3h)
|
||
780h "1"-bits synchronisation bits
|
||
<nn> lines data, format for each line as follows:
|
||
2 bytes origin of next line (lower byte first)
|
||
<xx> bytes data (xx = nextlineorg-currentlineorg-2)
|
||
2 bytes 0000h zero origin, no further lines following
|
||
7-8 bytes terminator, seven or eight 00h bytes
|
||
Note: The first line is assumed to begin at origin 8001h.
|
||
|
||
Format of MSX Binary Data Blocks (Type D0h)
|
||
780h "1"-bits synchronisation bits
|
||
2 bytes load address (lower byte first)
|
||
2 bytes end address ("")
|
||
2 bytes start address ("")
|
||
<len> bytes data (length = endadr-loadadr+1)
|
||
|
||
Format of MSX Ascii Data Blocks (Type EAh)
|
||
780h "1"-bits synchronisation bits
|
||
100h bytes data (ended by EOF/1Ah, unused bytes filled up by 1Ah)
|
||
More data blocks follow as long as the data block contains no EOF (1Ah).
|
||
|
||
Format of Bits and Bytes
|
||
The MSX BIOS generates start and stop bits for each byte:
|
||
1 start bit ("0")
|
||
8 data bits (lower bit first)
|
||
1 first stop bit ("1")
|
||
1 second stop bit ("1") (but might be unreadable if short delay follows)
|
||
And finally, the MSX bits themselves are encoded as follows:
|
||
"0" = \_______/"""""""\
|
||
"1" = \___/"""\___/"""\
|
||
Physically the signal looks less square, rather like a sine-wave.
|
||
(Note: The signal could be inverted, ie. high-pulse first...)
|
||
|
||
ROM Headers
|
||
-----------
|
||
|
||
The first 16 bytes of each Cartridge or Expansion ROM are used as header. In
|
||
most cases (ie. in game cartridges) only the first two entries are used, and
|
||
the remaing entries are set to zero.
|
||
Address Name Expl.
|
||
X000 ID Identification Code (4241h=ROM Cartridge, 4443h=SUBROM)
|
||
X002 INIT Start Address (could be anywhere 0000-BFFF)
|
||
X004 Statement Statement expansion routine address. For creating new
|
||
CALL statement (For example CALL MUSIC used in FM PAC)
|
||
X006 DEV For creating new devices (CAS:, MEM:, GRP:, etc...)
|
||
X008 TEXT Pointer to BASIC program in ROM, must be in 8000-BFFF.
|
||
X00A-F N/A Reserved (0)
|
||
Upon startup the BIOS scans all SLOTs for Cartridge ROMs (ID 4241h) at
|
||
addresses 4000h and 8000h, and for SUBROMs (ID 4443h) at address 0000h.
|
||
Most Cartridge ROMs occupy the area from 4000h-BFFFh, but might be also using
|
||
(or being mirrored to) the whole address space from 0000h to FFFFh.
|
||
|
||
Other DOCs
|
||
----------
|
||
|
||
Original doc by Mayer of WC Hakkers version 1.5 (PORTAR.DOC)
|
||
Documentation about MSX1/MSX2 and optional external hardware (IO ports).
|
||
ftp://ftp.funet.fi/pub/msx/txt/tech/portar.doc
|
||
|
||
TMS9918A VDP description/undocumented features by Sean Young
|
||
Documentation about MSX1 video display processor (VDP)
|
||
http://www.msxnet.org/tech/tms9918a.txt
|
||
|
||
The V9958-Registers by Zelly/Mayhem (V9958.TXT)
|
||
Brief (but VERY complete) summary about MSX2(+) VDP registers.
|
||
http: ???
|
||
|
||
The MSX Red Book by Avalon Software (TREDBOOK.TXT)
|
||
Documentation about
|
||
- MSX1 hardware (IO ports)
|
||
- MSX1 firmware (BIOS functions)
|
||
ftp://ftp.funet.fi/pub/msx/txt/tech/tredbook.arj
|
||
|
||
MSX2 Technical Handbook by Ascii Corp/Konami Man (TH-XX.TXT)
|
||
Verbose documentation about
|
||
- MSX2 hardware (IO ports)
|
||
- MSX2 firmware (BIOS functions)
|
||
- MSX2 software (BASIC and MSX-DOS commands)
|
||
http://www.geocities.com/SiliconValley/Bay/9797/msx2.htm#MSX2TH
|
||
|
||
Western Digital FD1793 Floppy Disk Controller (TECH_WD1793.HTM)
|
||
Unofficial Spectravideo Homepage by tomas.k (docs about FDC and other stuff)
|
||
http://home.swipnet.se/~w-16418/tech_wd1793.htm (old URL)
|
||
http://www.abysscrew.nu/spectravideo/ (new URL)
|
||
|
||
A22i CPC/Gameboy/MSX Assembler & Docs by Martin Korth (A22I.ZIP)
|
||
My MSX assembler for DOS, including a brief summary about
|
||
- Z80 instruction set (Opcodes, flags, clock cycles)
|
||
http://www.work.de/nocash/a22i.zip
|
||
|
||
No$msx Docs (an OLDER version of this file) by Martin Korth
|
||
http://www.work.de/nocash/msx-docs.zip
|
||
|
||
Kanji ROM Description (KANROM.TXT)
|
||
MSX Technical Guidebook from ASCAT / TAKAMICHI / G&T Soft International Div.
|
||
http://www.msxnet.org/gtinter/kanrom.htm
|
||
|
||
Others
|
||
PC-Profibuch by Martin Althaus (Sybex): 8253 Mode Register Info
|
||
|
||
END
|
||
|