commit 236275936e41bd0ec6ffe576ad8a799bd9c868da
parent 1be77dacc8f6e823835bbf7e9338e07f23d765a9
Author: Virgil Dupras <hsoft@hardcoded.net>
Date: Fri, 3 Jun 2022 08:24:54 -0400
Add some architecture documentation
Diffstat:
4 files changed, 100 insertions(+), 1 deletion(-)
diff --git a/README.md b/README.md
@@ -114,6 +114,8 @@ To build Dusk OS, you need:
Run `make` and then run `./dusk`. You'll get a prompt. Look at `xcomp.txt` and
`boot.fs` to have an idea of the vocabulary available. Type `bye` to quit.
+There is also some documentation in `/fs/doc`.
+
Dusk OS expects a raw input. With a regular TTY, your input will be buffered
and echoed twice. To avoid that, you can invoke it like this:
diff --git a/fs/doc/arch.txt b/fs/doc/arch.txt
@@ -0,0 +1,83 @@
+# Dusk OS Architecture
+
+# Subroutine Threaded Code
+
+This Forth is a Subroutine Thread Code (STC) Forth, that is, each reference to
+words is a native call instead of being a reference. This means that we don't
+have a "next" interpret loop. It's calls all the way down.
+
+# Caller save
+
+Native words don't save registers they use. For Forth words, it doesn't matter
+much because all words are "atomic". Once they return, register values don't
+matter anymore. Some native words call each other and this this case, careful
+threading is necessary, but otherwise, it works well as is.
+
+When other languages are concerned, however, this attribute becomes important
+because if a C expression calls a Forth word, then it loses register values.
+
+Therefore, it's important to remember that in Dusk OS, it's the caller
+responsibility to save/restore registers during a call.
+
+# Cross-compilation
+
+When we use the word "cross-compiled" below, it means that the binary that is
+being ran was not compiled by the system running it.
+
+# The layers of the system
+
+A running Dusk OS instance has several layers upon which the prompt is laid out.
+We try to keep a consistent terminology for each of those layers, this
+terminology is defined below.
+
+# Native Kernel (nkernel)
+
+This is the very core of the system, written in assembler and cross-compiled.
+It takes care of initializing all system variables, sets in< to boot< and then
+jump to the "mainloop" word of the fkernel (see below). It also defines the
+minimum set of words that allows the fkernel to "walk by itself", that is, to be
+able to continue chugging along through the bootstrapping process.
+
+In x86, the source for the nkernel is /dusk.asm.
+
+# Forth Kernel (fkernel)
+
+This layer is also cross-compiled, either by another Dusk OS instance (well,
+not yet because we're not self-hosting yet, but it will be the case soon enough)
+or by a POSIX system through nasm and /f2asm.py
+
+The source for the fkernel is in /xcomp.txt and is pseudo-Forth code. f2.asm.py
+is designed to be able to parse and compile it. Then Dusk OS will be
+self-hosting, a set of cross-compilation words will allow it to use the same
+source code to cross-compile another system.
+
+The role of the fkernel is to bring us "interpret+compile ready", that is, being
+able to run words from input and being able to define new words. It doesn't need
+to interpret user input, only forth code in memory.
+
+The fkernel ends with a "mainloop" word that is called by the nkernel upon
+boot. The mainloop is simple: it repeatedly read words from in< and interprets
+them.
+
+Because the nkernel has set in< to boot< before calling mainloop, what we're
+interpreting at this point is the contents of the next layer, the "boot"
+layer, which has been embedded in the Dusk OS binary and is being read from
+memory.
+
+# Boot layer (boot)
+
+At this point, we're done with cross-compiled binaries and we're now entirely
+on our own. Let's pick ourselves up by the bootstraps!
+
+The contents of /boot.fs has been embedded to the Dusk OS binary and is being
+read from memory. The role of the boot layer is to:
+
+1. Implement a minimally convenient set of words, such as comments, conditions
+ and loops, string literals, number formatting, create/value/alias.
+2. Give access to the root filesystem.
+3. Implement a user input system.
+
+Once it does that, it then spits the "Dusk OS" prompt and then switch in< to
+the user input.
+
+The system is yours.
diff --git a/fs/doc/x86.txt b/fs/doc/x86.txt
@@ -0,0 +1,14 @@
+# x86 architecture
+
+The x86 nkernel source code is /dusk.asm. Register roles:
+
+PSP: EBP
+RSP: ESP
+
+All other registers are free.
+
+For now, this nkernel needs to run on a Linux kernel and uses its syscalls
+for user interaction and file reading.
+
+It includes the boot source in its data section and makes boot< point to it
+at initialization.
diff --git a/xcomp.txt b/xcomp.txt
@@ -91,4 +91,4 @@ create tbl-0-f ," 0123456789abcdef"
word parse if r> if to then else
curword find not if (wnf) then
r> if to then execute stack? then ;
-: mainloop 0 'curword 5 + c! begin run1 again ;
+: mainloop begin run1 again ;