User Mode Simulator
Micronix uses the MPZ80 hardware to enforce memory protection and user/supervisor separation. when a Halt instruction (0x76) is executed, the processor saves state, changes the task map, switches to supervisor mode, and jumps to the kernel trap handler. the bytes following the Halt instruction specify the system call number and arguments.
Since sixth edition unix is a great-great grandfather of linux, it should be possible in a simulator to emulate all of the Z80 instruction set, and to translate the Micronix system calls into linux system calls.
this code is found in the usersim directory of the github repo.
I grabbed an accurate and fast Z80 instruction simulator in C with a wide-open license, Copyright (c) 2012-2017, from Lin Ke-Fong. It is well written, and designed to be nicely pluggable without much internal modification.
I then added the trap handlers and built an exec for the whitesmith binary format, added it to the instruction simulator, and now we can run Micronix binaries under Linux.
Sixth edition has far fewer system calls and signals, so there's a that just works, after translating addresses and arguments.
notable strangnesses include:
- no directory access system calls, with access to directory by reading the directory files directly. these contain an array of 16 bit i-numbers and a 14 character file name. I fake any reads of directory files into reads of a fake buffer that I build by calling the linux opendir/readdir.
- the tty driver is primitive, and the linux tty driver is way complex. the translation of stty/gtty is decidedly hacky.
- fork/wait/exit are just forwarded to linux. surprisingly, this mostly just works.
- there is no mkdir call. mknod is used with dev == 0, but does not automatically create . and .. links. the mkdir program issues explicit link calls for these, so we need to ignore them.
- unlink is used on directories too; there's no rmdir call.
- the location of the root can be specified on the command line to the simulator
- the empty path is equivalent to .
- lseek is in V7. the seek call has an option to specify block number or byte offset.
- we fake being root by specifying a command line option. this allows mknod to do a mkdir.
- I don't bother implementing quite a few system calls, like nice, kill, etc.
- signal 7 happens when the terminal has a character available; this allows primitive async character input.
- a lot of data types that we are used to be 32 bits are 16 bits in Micronix. pid, uid, gid, seek offset, signal mask and so on.
The simulator has pretty ridiculous logging, and a debug facility that can open an xterm, set breakpoints, watchpoints, tracing system calls, and so on.
as pretty much every C program I write, specifying -h to the simulator prints help and exits.
Note: If you get wierdness at startup of the sim, like it complaining about m10init not found, make sure that your userid is in the /etc/passwd file inside the filesystem.
this is an actual simulator session of the micronix user mode simulator running on a linux machine. The filesystem is whatever is in ../filesystem, and I've populated that with all the files I extracted from the micronix disks I could find. The C compiler from whitesmith's has a few serious limitations, but works.
It's a work in progress, and it is theoretically possible to do ps, /dev/mem, mount points, more tty's and raw disk devices.
UPM is the CP/M emulator under micronix, with good support for mapping drives to mount points, and so on, The man page is worth reading.
Yes, this is mbasic 5.21 running on a CP/M emulator running on a micronix emulator running inside a virtualbox centos VM on a macbook pro running OS-X, which is a BSD on top of Mach.