Matt J. Gumbley | Website:
Blog: On The Edge of Occam's Razor

PsiXZX Psion Series 3 Spectrum Emulator

Table Of COntents

1 Introduction

This project or information is dead. I cannot release any code or further information on it, other than what you'll find on this page. All communication regarding it will be silently deleted. Apologies.

PsiXZX is a port of the XZX ZX Spectrum Emulator to the EPOC 16 platform. There's not a lot of information available yet, and nothing you can really try out, I'm afraid...

2 Availability

It isn't available yet. Erik Kunze, the main author of the XZX emulator has asked me to merge the Psion port with the UNIX/X11 source tree. Since I ported this as a very quick hack to see if it was feasible, I hacked away at his source with great relish. There's little of the base XZX code left intact.. it'll take a while to comply with his wishes (see comments about whether I can be bothered continuing with this)...

3 Limitations

This is an extremely slow emulator, even running under the EPOC 16 Emulators on high-speed PCs. I'm working to improve matters by optimising it, but it'll never run in real-time on a real Psion.

It emulates a 48KB standard ZX Spectrum, with no additional interfaces. There is no support for sound, and the attribute (colour) handling isn't implemented. Keyboard handling needs some more work, and there's no snapshot loader yet. Spectrum BASIC seems to work OK though, if you're prepared for a wait. Timing isn't as accurate as the XZX emulator which this program uses as its base.

The Spectrum screen is 256x192 pixels - taller than a Psion screen. I haven't yet added any screen scrolling routines to enable the screen to be viewed on a real Psion; I simply changed the emulator's configuration to give me a larger screen.

There's a lot of work still to do. Although several people have expressed an interest in seeing this run on a real Psion, I'm not entirely sure it's worth the effort. It does run extremely slowly.

4 Why it's so slow

The Z80 emulator in XZX uses a large switch() statement to process each Z80 opcode. The extended opcodes are handled by nested switch() statements. Thus, the resulting emulator main loop is VERY large. Several UNIX compilers cannot compile it, and Topspeed C won't compile it either. Therefore, I've had to break the switch() statement down into separate functions which handle each opcode, and a function-pointer table. This imposes an additional lookup and jump/return per opcode, which slows things down somewhat.

The Z80 has a 64KB memory map, with the Spectrum's 16KB ROM mapped in at the start of memory, followed by the screen RAM, then the user RAM. Since EPOC 16 only allows a single 64KB code and 64KB data segment per process, an additional segment has had to be allocated as the emulated computer's memory. Accessing this memory has to be done using EPOC system calls. This slows down each memory access considerably. There is some optimisation to be done using assembly language inline access, if possible.

The screen bitmap is held in another separate segment, and is accessed in the same manner. When a write to Spectrum screen memory is performed, the write is done to the main memory segment, and then processed, and done to the Psion screen bitmap. Since the bitmap is in a separate segment, the EPOC OS calls have to be done, slowing things down even more...

5 Why the keyboard handling is so bad

When a key is pressed on a real Spectrum, certain bits of an I/O port are lowered. When the key is released, these bits are raised. So, simply map key presses and releases onto bits of this I/O port. Except that (AFAIK) you can't detect when a key has been released in EPOC 16. Also, the Spectrum OS performs key rollover, and so a key has to be pressed for a certain duration before it is accepted. So, a system of counters has been added. When a key is pressed, the appropriate bit(s) in the port are lowered, and a counter set to a value. When the port is read, the keypress is registered, and the counter decremented. When the counter reaches zero, the appropriate bit is raised, simulating a key release. It works, but it's a kludge, and games probably won't like it.

6 Wot no colour?

I couldn't be bothered :-)

The screen is used as a black-and-white image, the grey plane of the screen bitmap is not yet used.

7 Why won't it load Jet Set Willy?

Because I haven't added the snapshot loader yet. You could always write a clone in Spectrum BASIC. And type it in every time you want to play it :-)

8 So emulation on a Series 3 is a no-go, then?

I wouldn't say that... it does work, but we're only using an NEC V30H at 7.68MHz so don't expect anything fast. Emulation is a very time consuming process. The Z80 is quite a complex processor, IMHO. Simpler processors (such as the 6502) would be easier to emulate. This doesn't mean that a Commodore 64 would be simple to emulate - that machine had some quite complex hardware. The Spectrum's appeal lies in the incredible simplicity of the hardware. It's relatively simple to emulate. I could rewrite PsiXZX's core in assembler, but a) I'd really rather have root canal work done with a Bosch hammer drill and b) it might not gain much speed. Certain parts can be improved, and if these don't make it worthwhile, I'll abandon the project.

If I do anything more with emulation on the '3, I'd look at porting an Apple //e emulator, since I've got a real //e, they're rather nice machines, and I've got plenty of technical info to work from. Anyone else interested? (I just want to play Fooblitzky again...)

9 Hasn't the Gameboy got a Z80?

I believe so. I haven't looked for any technical information on it. It may be possible to adapt PsiXZX into PsiGameboy, yes. Mail me what you have....
(C) Matt J. Gumbley 1998-2005 - All Tights Reversed