From 8923fefeffc792dd6f654f83901a3b80ab0bf999 Mon Sep 17 00:00:00 2001 From: Virgil Dupras Date: Mon, 20 May 2019 12:11:45 -0400 Subject: [PATCH] Update docs --- README.md | 105 ++++++++++++++++++++++--------------------- doc/emulate.md | 6 +-- doc/glue-code.md | 39 ++++++++++------ doc/load-run-code.md | 6 +-- tools/emul/README.md | 53 +++++++++++++++------- 5 files changed, 124 insertions(+), 85 deletions(-) diff --git a/README.md b/README.md index e7405c0..3fadb1d 100644 --- a/README.md +++ b/README.md @@ -2,8 +2,8 @@ *Bootstrap post-collapse technology* -Collapse OS is a collection of programs, tools and documentation that allows -you to assemble an OS that can: +Collapse OS is a z80 kernel and a collection of programs, tools and +documentation that allows you to assemble an OS that can: 1. Run on an extremely minimal and improvised architecture. 2. Communicate through a improvised serial interface linked to some kind of @@ -20,7 +20,23 @@ manage to build and install Collapse OS without external resources (i.e. internet) on a machine of her design, built from scavenged parts with low-tech tools. -See the "Goals" section below for details. +## Status + +The project is progressing well! Highlights: + +* Has a shell that can poke memory, I/O, call arbitrary code from memory. +* Can "upload" code from serial link into memory and execute it. +* Can manage multiple "block devices" +* Can read SD cards as block devices +* A z80 assembler, written in z80 that is self-assembling and can assemble the + whole project. 4K binary, uses less than 16K of memory to assemble the kernel + or itself. +* Extremely flexible: Kernel parts are written as loosely knit modules that + are bound through glue code. This makes the kernel adaptable to many unforseen + situations. +* A typical kernel binary of less than 2K (but size vary wildly depending on + parts you include). +* Built with minimal tooling: only [libz80][libz80] is needed ## Why? @@ -78,26 +94,6 @@ enough to steadily improve your technological situation, build more sophisticated machines from more sophisticated scavenged parts and, who knows, in a couple of decades, build a new IC fab (or bring an old one back to life). -## Status - -The project is progressing well and I already have a working shell (see `doc` -to see what it can do) on a classic RC2014. Highlights: - -* Extremely flexible: Kernel parts are written as loosely knit modules that - are bound through glue code. This makes the kernel adaptable to many unforseen - situations. -* 2K binary (but size vary wildly depending on what parts you include. 2K is - for a shell using all parts). -* Built with minimal tooling: only [scas][scas] is needed -* Can read and write to memory through shell -* Can run arbitrary routine from arbitrary address with arbitrary arguments - from shell. -* Can "upload" code from serial link into memory and execute it. -* Can manage multiple "block devices" -* Can read SD cards as block devices -* A z80 assembler written in z80 that is progressing well and should soon be - able to replace `scas`. - ## Organisation of this repository There's very little done so far, but here's how it's organized: @@ -107,40 +103,49 @@ There's very little done so far, but here's how it's organized: * `recipes`: collection of recipes that assemble parts together on a specific machine. * `doc`: User guide for when you've successfully installed Collapse OS. +* `tools`: Tools for working with Collapse OS from "modern" environments. Mostly + development tools, but also contains emulated zasm, which is + necessary to build Collapse OS from a non-Collapse OS machine. Each folder has a README with more details. ## Roadmap -Such a vast project involves quite a lot of fiddling and I can't really have a -precise roadmap, only a general direction: +The roadmap used to be really hazy, but with the first big goal (that was to +have a self-assembling system) reached, the feasability of the project is much +more likely and the horizon is clearing out. -The primary target for Collapse OS is the z80 architecture. There's a good -amount of great z80-related hacks all around the internet, and the z80 CPU is -very scavenge-friendly: it's been (and is) included in tons of devices. +As of now, that self-assembling system is hard to use outside of an emulated +environment, so the first goal is to solidify what I have. -After a good proof of concept is done in z80, then more architectures can be -added into the mix. I have the intuition that we can mix AVR and z80 in a very -elegant minimal and powerful machine and it would be great if a Collapse OS -spawn could be built for such machine. +1. Error out gracefully in ZASM. It can compile almost any valid code that scas + can, but it has undfined behavior on invalid code and that make it very hard + to use. +2. Make shell, CFS, etc. convenient enough to use so that I can easily assemble + code on an SD card and write the binary to that same SD card from within a + RC2014. -I'm planning to go forward with this project by doing three things: +After that, then it's the longer term goals: -1. Gather knowledge and hone skills. -2. Build useful parts of code to be assembled into an OS by the user. -3. Write "recipes", examples of assembly on real machines using parts I wrote - to serve as a guide for post-collapse assembly. +1. Get out of the serial link: develop display drivers for a vga output card + that I have still to cobble up together, then develop input driver for some + kind of PS/2 interface card I'll have to cobble up together. +2. Add support for writing to flash/eeprom from the RC2014. +3. Add support for floppy storage. +4. Add support for all-RAM systems through bootloading from storage. -Recipes should contain both "pre-collapse" instructions (how to build Collapse -OS from a "modern" system) and "post-collapse" instructions (how to build -Collapse OS from itself). +Then comes the even longer term goals, that is, widen support for all kind of +machines and peripherals. It's worth mentionning, however, that supporting +*specific* peripherals isn't on the roadmap. There's too many of them out there +and most peripheral post-collapse will be cobbled-up together anyway. -Initially, we of course only have "pre-collapse" instructions, but as tooling -improve, the "post-collapse" part will become more and more complete. When we -have complete "post-collapse" recipes, we can call it a win. +The goal is to give good starting point for as many *types* of peripherals +possible. -If you're interested in being part of this project, I have no idea how to -include you, but please, let me know, we'll manage something. +It's also important to keep in mind that the goal of this OS is to program +microcontrollers, so the type of peripherals it needs to support is limited +to whatever is needed to interact with storage, serial links, display and +receive text, do bit banging. ## Open questions @@ -172,14 +177,14 @@ First, because I think there are more scavenge-friendly 8-bit chips around than scavenge-friendly 16-bit or 32-bit chips. Second, because those chips will be easier to replicate in a post-collapse fab. -If the first chips we're able to create post-collapse are low-powered, we might -as well design a system that works well on low-powered chips. +The z80 has 9000 transistors. 9000! Compared to the millions we have in any +modern CPU, that's nothing! If the first chips we're able to create +post-collapse have a low transistor count, we might as well design a system +that works well on simpler chips. That being said, nothing stops the project from including the capability of programming an ARM or RISC-V chip. -That being said, the MSP430 seems like a really nice and widely used chip... - ### Prior art I've spent some time doing software archeology and see if something that was @@ -212,4 +217,4 @@ sound more or less crazy to you than what you've been reading in this text so far?), I will probably need help to pull this off. [searle]: http://searle.hostei.com/grant/z80/SimpleZ80.html -[scas]: https://github.com/KnightOS/scas +[libz80]: https://github.com/ggambetta/libz80 diff --git a/doc/emulate.md b/doc/emulate.md index bb04312..367c9c7 100644 --- a/doc/emulate.md +++ b/doc/emulate.md @@ -2,7 +2,7 @@ The quickest way to give Collapse OS a whirl is to use `tools/emul` which is built around [libz80][libz80]. Everything is set up, you just have to run -`make`. +`make`, then `shell/shell`. To emulate something at a lower level, I recommend using Alan Cox's [RC2014 emulator][rc2014-emul]. It runs Collapse OS fine but you have to write the @@ -13,13 +13,13 @@ A working Makefile for a project with a glue code being called `main.asm` could look like: TARGET = os.bin - PARTS = ~/collapseos/parts + ZASM = ~/collapseos/tools/emul/zasm/zasm ROM = os.rom .PHONY: all all: $(ROM) $(TARGET): main.asm - scas -o $@ -L map -I $(PARTS) $< + $(ZASM) < $< > $@ $(ROM): $(TARGET) cp $< $@ diff --git a/doc/glue-code.md b/doc/glue-code.md index 0d07b0d..54404a7 100644 --- a/doc/glue-code.md +++ b/doc/glue-code.md @@ -1,15 +1,16 @@ # Writing the glue code -Collapse OS is not an OS, it's a meta OS. It supplies parts that you're expected -to glue together in a "glue code" asm file. Here is what a minimal glue code -for a shell on a Classic [RC2014][rc2014] with an ACIA link would look like: +Collapse OS's kernel code is loosely knit. It supplies parts that you're +expected to glue together in a "glue code" asm file. Here is what a minimal +glue code for a shell on a Classic [RC2014][rc2014] with an ACIA link would +look like: ; The RAM module is selected on A15, so it has the range 0x8000-0xffff - RAMSTART .equ 0x8000 - RAMEND .equ 0xffff - ACIA_CTL .equ 0x80 ; Control and status. RS off. - ACIA_IO .equ 0x81 ; Transmit. RS on. + .equ RAMSTART 0x8000 + .equ RAMEND 0xffff + .equ ACIA_CTL 0x80 ; Control and status. RS off. + .equ ACIA_IO 0x81 ; Transmit. RS on. jr init @@ -29,18 +30,28 @@ for a shell on a Classic [RC2014][rc2014] with an ACIA link would look like: jp shellLoop #include "core.asm" - ACIA_RAMSTART .equ RAMSTART + .equ ACIA_RAMSTART RAMSTART #include "acia.asm" - SHELL_RAMSTART .equ ACIA_RAMEND + .equ SHELL_RAMSTART ACIA_RAMEND .define SHELL_GETC call aciaGetC .define SHELL_PUTC call aciaPutC .define SHELL_IO_GETC call aciaGetC - SHELL_EXTRA_CMD_COUNT .equ 0 + .equ SHELL_EXTRA_CMD_COUNT 0 #include "shell.asm" -Once this is written, building it is easy: +Once this is written, building it is easy: - scas -o collapseos.bin -I /path/to/parts glue.asm + zasm < glue.asm > collapseos.bin + +## Building zasm + +Collapse OS has its own assembler written in z80 assembly. We call it +[zasm][zasm]. Even on a "modern" machine, it is that assembler that is used, +but because it is written in z80 assembler, it needs to be emulated (with +[libz80][libz80]). + +So, the first step is to build zasm. Open `tools/emul/README.md` and follow +instructions there. ## Platform constants @@ -106,7 +117,7 @@ effective, only works for one table per part. But it's often enough. For example, to define extra commands in the shell: [...] - SHELL_EXTRA_CMD_COUNT .equ 2 + .equ SHELL_EXTRA_CMD_COUNT 2 #include "shell.asm" .dw myCmd1, myCmd2 [...] @@ -118,3 +129,5 @@ and this much depends on the part you select. But if you want a shell, you will usually end it with `shellLoop`, which never returns. [rc2014]: https://rc2014.co.uk/ +[zasm]: ../tools/emul/README.md +[libz80]: https://github.com/ggambetta/libz80 diff --git a/doc/load-run-code.md b/doc/load-run-code.md index 692dd01..db18c25 100644 --- a/doc/load-run-code.md +++ b/doc/load-run-code.md @@ -16,7 +16,7 @@ machine: (we must always return at the end of code that we call with `call`). This will increase a number at memory address `0xa100`. First, compile it: - scas -o tosend.bin tosend.asm + zasm < tosend.asm > tosend.bin Now, we'll send that code to address `0xa000`: @@ -108,8 +108,8 @@ like (important fact: `jp ` uses 3 bytes): It then becomes easy to build yourself a predictable and stable jump header, something you could call `jumptable.inc`: - JUMP_PRINTSTR .equ 0x03 - JUMP_ACIAPUTC .equ 0x06 + .equ JUMP_PRINTSTR 0x03 + .equ JUMP_ACIAPUTC 0x06 You can then include that file in your "user" code, like this: diff --git a/tools/emul/README.md b/tools/emul/README.md index 77ec404..3b43f52 100644 --- a/tools/emul/README.md +++ b/tools/emul/README.md @@ -1,10 +1,22 @@ # emul -This is an emulator for a virtual machine that is suitable for running Collapse -OS. The goal of this machine is not to emulate real hardware, but rather to -serve as a development platform. What we do here is we emulate the z80 part, -the 64K memory space and then hook some fake I/Os to stdin, stdout and a small -storage device that is suitable for Collapse OS's filesystem to run on. +This folder contains a couple of tools running under the [libz80][libz80] +emulator. + +## Build + +First, make sure that the `libz80` git submodule is checked out. If not, run +`git submodule init && git submodule update`. + +After that, you can run `make` and it builds all tools. + +## shell + +Running `shell/shell` runs the shell in an emulated machine. The goal of this +machine is not to simulate real hardware, but rather to serve as a development +platform. What we do here is we emulate the z80 part, the 64K memory space and +then hook some fake I/Os to stdin, stdout and a small storage device that is +suitable for Collapse OS's filesystem to run on. Through that, it becomes easier to develop userspace applications for Collapse OS. @@ -13,26 +25,35 @@ We don't try to emulate real hardware to ease the development of device drivers because so far, I don't see the advantage of emulation versus running code on the real thing. -## Bootstrapped binary +## zasm -The file `zasm/zasm.bin` is a compiled binary for `apps/zasm/glue.asm`. It is +`zasm/zasm` is `apps/zasm` wrapped in an emulator. It is quite central to the +Collapse OS project because it's used to assemble everything, including itself! + +The program takes no parameter. It reads source code from stdin and spits +binary in stdout. It supports includes and had both `apps/` and `kernel` folder +packed into a CFS that was statically included in the executable at compile +time. + +The file `zasm/zasm.bin` is a compiled binary for `apps/zasm/glue.asm` and +`zasm/kernel.bin` is a compiled binary for `tools/emul/zasm/glue.asm`. It is used to bootstrap the assembling process so that no assembler other than zasm is required to build Collapse OS. This binary is fed to libz80 to produce the `zasm/zasm` "modern" binary and -once you have that, you can recreate `zasm/zasm.bin`. +once you have that, you can recreate `zasm/zasm.bin` and `zasm/kernel.bin`. This is why it's included as a binary in the repo, but yes, it's redundant with the source code. -## Usage +Those binaries can be updated with the `make updatebootstrap` command. If they +are up-to date and that zasm isn't broken, this command should output the same +binary as before. -First, make sure that the `libz80` git submodule is checked out. If not, run -`git submodule init && git submodule update`. +## runbin -The Makefile in this folder has multiple targets that all use libz80 as its -core. For example, `make shell` will build `./shell`, a vanilla Collapse OS -shell. `make zasm` will build a `./zasm` executable, and so on. +This is a very simple tool that reads binary z80 code from stdin, loads it in +memory starting at address 0 and then run the code until it halts. The exit +code of the program is the value of `A` when the program halts. -See documentation is corresponding source files for usage documentation of -each target. +This is used for unit tests.