-
-
Notifications
You must be signed in to change notification settings - Fork 44
/
README
346 lines (264 loc) · 14.8 KB
/
README
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
________________ ________________ _________________
| /\ | || |
|_______ / / | ____ || ____ |
\_____/ / / | |____| || |___/| |
/ / / | || | | | |
/ / / | ____ || | | | |
/ /_/_____| |____| || |__|_| |
/ || || |
/_______________||________________||________________|
\________________\\______________//________________/
______________________________________________________________________________
| |
| Zilog Z80 CPU Emulator |
| version 0.2 |
| |
| Copyright (C) 1999-2024 Manuel Sainz de Baranda y Goñi |
| Released under the terms of the GNU Lesser General Public License v3 |
| |
| https://zxe.io/software/Z80 |
| |
'=============================================================================='
1. Introduction
================
The Z80 library implements a fast, small and accurate emulator of the Zilog Z80.
It emulates all that is known to date about this CPU, including the undocumented
behaviors, MEMPTR, Q and the special RESET. It also has the honor of having been
the first open-source project to provide full emulation of the interrupt mode 0.
The source code is written in ANSI C for maximum portability and is extensively
commented. The aim has been to write a well-structured, easy-to-understand piece
of software; something solid and elegant that can stand the test of time with no
need for major changes.
2. Accuracy
============
This Z80 CPU emulator has a classic design with instruction-level granularity
that delivers the best performance, whilst offering a reasonable flexibility to
achieve precision down to the T-state level.
Instruction-level granularity implies that, except in a few well-defined cases,
the execution of a given instruction cannot stop until all its internal M-cycles
have been processed (i.e., instructions are not divided into micro-operations).
Moreover, registers are modified only once per instruction and the T-state
counter is normally updated after a full instruction has been executed.
That said, instructions, flags, memory accesses, interrupts, clock cycles, etc.,
are accurately emulated according to the available technical documentation, the
findings made after decades of research on the Z80 and electronic simulations.
And, of course, the emulator passes the most exhaustive tests written to date,
such as Frank D. Cringle's "Z80 Instruction Set Exerciser", Mark Woodmass' "Z80
Test Suite", Patrik Rak's "Zilog Z80 CPU Test Suite" and Peter Helcmanovsky's
"Z80 Block Flags Test", to name a few.
3. Installation from sources
=============================
You will need CMake v3.14 or later to build the package and, optionally, recent
versions of Doxygen, Sphinx and Breathe to compile the documentation. Also, make
sure that you have LaTeX with PDF support installed on your system if you want
to generate the documentation in PDF format.
The emulator requires some types and macros included in Zeta (https://zeta.st),
a dependency-free, header-only library used to retain compatibility with most C
compilers. Install Zeta or extract its source code tarball to the root directory
of the Z80 project or its parent directory. Zeta is the sole dependency; the
emulator is a freestanding implementation and as such does not depend on the C
standard library.
Once the prerequisites are met, create a directory and run `cmake` from there to
prepare the build system:
$ mkdir build
$ cd build
$ cmake [options] <Z80-project-directory>
The resulting build files can be configured by passing options to `cmake`. To
show a complete list of those available along with their current settings, type
the following:
$ cmake -LAH -N -B .
If in doubt, read the CMake documentation for more information on configuration
options. The following are some of the most relevant standard options of CMake:
-DBUILD_SHARED_LIBS=(YES|NO)
Generate shared libraries rather than static libraries.
The default is `NO`.
-DCMAKE_BUILD_TYPE=(Debug|Release|RelWithDebInfo|MinSizeRel)
Choose the type of build (configuration) to generate.
The default is `Release`.
-DCMAKE_INSTALL_NAME_DIR="<path>"
Specify the directory portion of the dynamic library install name on
Apple platforms (for installed shared libraries).
Not defined by default.
-DCMAKE_INSTALL_PREFIX="<path>"
Specify the installation prefix.
The default is `/usr/local` (on UNIX and UNIX-like operating systems).
Package-specific options are prefixed with `Z80_` and can be divided into two
groups. The first one controls aspects not related to the source code of the
library:
-DZ80_DEPOT_LOCATION="<location>"
Specify the directory or URL of the depot containing the test files
(i.e., the firmware and software required by the testing tool).
The default is `http://zxe.io/depot`.
-DZ80_FETCH_TEST_FILES=(YES|NO)
Copy or download the test files from the depot to the build directory.
The default is `NO`.
-DZ80_INSTALL_CMAKEDIR="<path>"
Specify the directory in which to install the CMake config-file package.
The default is `"${CMAKE_INSTALL_LIBDIR}/cmake/Z80"`.
-DZ80_INSTALL_PKGCONFIGDIR="<path>"
Specify the directory in which to install the pkg-config file.
The default is `"${CMAKE_INSTALL_LIBDIR}/pkgconfig"`.
-DZ80_NOSTDLIB_FLAGS=(Auto|"[<flag>[;<flag>...]]")
Specify the linker flags used to avoid linking against system libraries.
The default is `Auto` (autoconfigure flags). If you get linker errors,
set this option to `""`.
-DZ80_OBJECT_LIBS=(YES|NO)
Build the emulator as an object library.
This option takes precedence over `BUILD_SHARED_LIBS` and
`Z80_SHARED_LIBS`. If enabled, the build system will ignore
`Z80_WITH_CMAKE_SUPPORT` and `Z80_WITH_PKGCONFIG_SUPPORT`, as no
libraries or support files will be installed.
The default is `NO`.
-DZ80_SHARED_LIBS=(YES|NO)
Build the emulator as a shared library, rather than static.
This option takes precedence over `BUILD_SHARED_LIBS`.
Not defined by default.
-DZ80_SPHINX_HTML_THEME="[<name>]"
Specify the Sphinx theme for the documentation in HTML format.
The default is `""` (use the default theme).
-DZ80_WITH_CMAKE_SUPPORT=(YES|NO)
Generate and install the CMake config-file package.
The default is `NO`.
-DZ80_WITH_HTML_DOCUMENTATION=(YES|NO)
Build and install the documentation in HTML format.
It requires Doxygen, Sphinx and Breathe.
The default is `NO`.
-DZ80_WITH_PDF_DOCUMENTATION=(YES|NO)
Build and install the documentation in PDF format.
It requires Doxygen, Sphinx, Breathe, and LaTeX with PDF support.
The default is `NO`.
-DZ80_WITH_PKGCONFIG_SUPPORT=(YES|NO)
Generate and install the pkg-config file.
The default is `NO`.
-DZ80_WITH_STANDARD_DOCUMENTS=(YES|NO)
Install the standard text documents distributed with the package:
AUTHORS, COPYING, COPYING.LESSER, HISTORY, README and THANKS.
The default is `NO`.
-DZ80_WITH_TESTS=(YES|NO)
Build the testing tool.
The default is `NO`.
The second group of package-specific options configures the source code of the
library by predefining macros that enable optional features:
-DZ80_WITH_EXECUTE=(YES|NO)
Build the implementation of the `z80_execute` function.
The default is `NO`.
-DZ80_WITH_FULL_IM0=(YES|NO)
Build the full implementation of the interrupt mode 0 rather than the
reduced one.
The default is `NO`.
-DZ80_WITH_IM0_RETX_NOTIFICATIONS=(YES|NO)
Enable optional notifications for any `reti` or `retn` instruction
executed during the interrupt mode 0 response.
The default is `NO`.
-DZ80_WITH_Q=(YES|NO)
Build the implementation of Q.
The default is `NO`.
-DZ80_WITH_SPECIAL_RESET=(YES|NO)
Build the implementation of the special RESET.
The default is `NO`.
-DZ80_WITH_UNOFFICIAL_RETI=(YES|NO)
Configure the undocumented instructions ED5Dh, ED6Dh and ED7Dh as `reti`
instead of `retn`.
The default is `NO`.
-DZ80_WITH_ZILOG_NMOS_LD_A_IR_BUG=(YES|NO)
Build the implementation of the bug affecting the Zilog Z80 NMOS, which
causes the P/V flag to be reset when a maskable interrupt is accepted
during the execution of the `ld a,{i|r}` instructions.
The default is `NO`.
Package maintainers are encouraged to use at least the following options for the
shared library:
-DZ80_WITH_EXECUTE=YES
-DZ80_WITH_FULL_IM0=YES
-DZ80_WITH_IM0_RETX_NOTIFICATIONS=YES
-DZ80_WITH_Q=YES
-DZ80_WITH_ZILOG_NMOS_LD_A_IR_BUG=YES
Finally, once the build system is configured according to your needs, build and
install the package:
$ cmake --build . [--config (Debug|Release|RelWithDebInfo|MinSizeRel)]
# cmake --install . [--config <configuration>] [--strip]
The `--config` option is only necessary for those CMake generators that ignore
`CMAKE_BUILD_TYPE` (e.g., Xcode and Visual Studio). Use `--strip` to remove
debugging information and non-public symbols when installing non-debug builds of
the shared library.
4. Integration
===============
4.1. As an external dependency in CMake-based projects
The Z80 library includes a config-file package for integration into CMake-based
projects that must be installed for development. Use `find_package` to find the
`Z80` package. This creates the `Z80` imported library target, which carries the
necessary transitive link dependencies. Optionally, the linking method can be
selected by specifying either the `Shared` or `Static` component.
Example:
find_package(Z80 REQUIRED Shared)
target_link_libraries(your-target Z80)
When not specified as a component, the linking method is selected according to
`Z80_SHARED_LIBS`. If this option is not defined, the config-file uses the type
of library that is installed on the system and, if it finds both the shared and
the static versions, `BUILD_SHARED_LIBS` determines which one to link against.
4.2. As a CMake subproject
To embed the Z80 library as a CMake subproject, extract the source code tarballs
of Zeta (https://zeta.st) and Z80 (or clone their respective repositories) into
a subdirectory of another project. Then use `add_subdirectory` in the parent
project to add the Z80 source code tree to the build process (N.B., the Z80
subproject will automatically find Zeta and import it as an interface library).
It is advisable to configure the Z80 library in the CMakeLists.txt of the parent
project. This will prevent the user from having to specify configuration options
for the Z80 subproject through the command line when building the main project.
See section 3 of this document for a list of available configuration options.
Example:
set(Z80_SHARED_LIBS NO CACHE BOOL "")
set(Z80_WITH_Q YES CACHE BOOL "")
set(Z80_WITH_ZILOG_NMOS_LD_A_IR_BUG YES CACHE BOOL "")
add_subdirectory(dependencies/Z80)
target_link_libraries(your-target Z80)
It is important to set the `Z80_SHARED_LIBS` option. Otherwise, CMake will build
the library type indicated by `BUILD_SHARED_LIBS`, which may not be the desired
one.
4.3. Non-CMake-based projects
The source code of the emulator can be configured at compile time by predefining
a series of macros. Both Z80.h and Z80.c obey the first two explained below. The
rest of the macros are only relevant when compiling Z80.c:
#define Z80_EXTERNAL_HEADER "header-name.h"
Specifies the only external header to `#include`, replacing all others.
Predefine this macro to provide a header file that defines the external
types and macros used by the emulator, thus preventing your project from
depending on Zeta. You can use this when compiling Z80.c as a part of
your project or (if your types do not break the binary compatibility)
when including `<Z80.h>` and linking against a pre-built Z80 library.
#define Z80_STATIC
Restricts the visibility of public symbols.
This macro is required if you are building Z80.c as a static library,
compiling it directly as a part of your project, or linking your program
against the static version of the Z80 library. In either of these cases,
make sure this macro is defined before including `"Z80.h"` or `<Z80.h>`.
#define Z80_WITH_LOCAL_HEADER
Tells Z80.c to `#include "Z80.h"` instead of `<Z80.h>`.
The optional features of the emulator mentioned in section 3 of this document
are disabled by default. If you compile Z80.c as a part of your project, enable
those features you need by predefining their respective activation macros. They
have the same name as their CMake equivalents:
#define Z80_WITH_EXECUTE
#define Z80_WITH_FULL_IM0
#define Z80_WITH_IM0_RETX_NOTIFICATIONS
#define Z80_WITH_Q
#define Z80_WITH_SPECIAL_RESET
#define Z80_WITH_UNOFFICIAL_RETI
#define Z80_WITH_ZILOG_NMOS_LD_A_IR_BUG
Except for `Z80_EXTERNAL_HEADER`, the above macros can be empty; the source code
only checks whether they are defined.
Please note that the activation of some of the optional features affects the
speed of the emulator due to various factors (read the documentation for more
details).
5. License
===========
This library is free software: you can redistribute it and/or modify it under
the terms of the GNU Lesser General Public License as published by the Free
Software Foundation, either version 3 of the License, or (at your option) any
later version.
This library is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public License along
with this library. If not, see <http://www.gnu.org/licenses/>.
________________________________________________________________________________
Last update: 2024-11-18 README EOF