From 5a41189405de0865daa087aceced43b04258c1d6 Mon Sep 17 00:00:00 2001 From: d_m Date: Mon, 5 Aug 2024 22:09:53 -0400 Subject: [PATCH] Add uxntal manpage. This change adds uxntal.7 [1]. It also updates the makefile to install the executables and man page in ~/.local (~/.local/bin and ~/.local/share/man respectively). This can easily be overridden by using PREFIX, for example: # install into home directory make PREFIX=$HOME install # install into /usr/local make PREFIX=/usr/local install Finally, it updates the README to describe these things. [1] Origin: https://git.phial.org/d6/nxu/raw/branch/main/uxntal.7 --- README.md | 24 ++++ doc/man/uxntal.7 | 363 +++++++++++++++++++++++++++++++++++++++++++++++ makefile | 9 +- 3 files changed, 394 insertions(+), 2 deletions(-) create mode 100644 doc/man/uxntal.7 diff --git a/README.md b/README.md index 23153ad..798c132 100644 --- a/README.md +++ b/README.md @@ -4,6 +4,20 @@ An emulator for the [Uxn stack-machine](https://wiki.xxiivv.com/site/uxn.html), ## Building +### Makefile + +For your convenience a [Makefile](https://en.wikipedia.org/wiki/Make_(software)#Makefile) is provided. You can run `make install` to build and install the files. + +By default, files are installed into `~/.local` but this can be overridden using `PREFIX`: + +```sh +# installs files into ~/.local/bin and ~/.local/share +$ make install + +# installs files into /opt/uxn/bin and /opt/uxn/share +$ make PREFIX=/opt/uxn install +``` + ### Graphical All you need is X11. @@ -32,6 +46,16 @@ The first parameter is the rom file, the subsequent arguments will be accessible bin/uxnemu bin/polycat.rom arg1 arg2 ``` +## Manual + +A manual page is provided documenting the Uxntal language: + +```sh +man ./doc/man/uxntal.7 +``` + +After running `make install` the man page should be found by `man uxntal`. + ## Devices The file device is _sandboxed_, meaning that it should not be able to read or write outside of the working directory. diff --git a/doc/man/uxntal.7 b/doc/man/uxntal.7 new file mode 100644 index 0000000..ef03077 --- /dev/null +++ b/doc/man/uxntal.7 @@ -0,0 +1,363 @@ +.\" Manpage reference for uxntal. +.\" by Eiríkr Åsheim +.\" Contact d_m@plastic-idolatry.com to correct errors or typos. +.TH uxntal 7 "05 Aug 2024" "1.0" "Uxntal Reference Guide" +.SH NAME +uxntal \- assembly langauge for Varvara virtual machine +.SH DESCRIPTION +Uxntal is an 8-bit instruction set for programming the Varvara virtual machine. +It uses the lower 5-bits to specify an opcode, and the upper 3-bits to specify +optional modes. + +ROMs consist of a 16-bit address space of bytes. Any byte can be interpreted as either data or an instruction. A 2-byte program counter (\fIpc\fP) determines the address of the next instruction to decode and run. + +Instructions manipulate data using two stacks: a working stack (\fBwst\fP) and a return stack (\fBrst\fP). Each stack consists of 256 bytes, and in the case of overflow or underflow the stack pointer will wrap (the stacks are circular). + +There are also 256 bytes of device memory, which are used to interact with the virtual machine and its devices. + +Instructions deal with unsigned 8-bit values (\fIbytes\fP) and unsigned 16-bit values (\fIshorts\fP). There are no other built-in data types. + +.SH INSTRUCTION LAYOUT + + 0x01 ---- + 0x02 \\ + 0x04 +- \fIopcode\fP + 0x08 / + 0x10 ---- + 0x20 ---- 2: \fIshort mode\fP + 0x40 ---- r: \fIreturn mode\fP + 0x80 ---- k: \fIkeep mode\fP + +.SH OPCODE LAYOUT + +There are 32 base values for opcodes: + + 0x00 \fBBRK*\fP 0x08 \fBEQU\fP 0x10 \fBLDZ\fP 0x18 \fBADD\fP + 0x01 \fBINC\fP 0x09 \fBNEQ\fP 0x11 \fBSTZ\fP 0x19 \fBSUB\fP + 0x02 \fBPOP\fP 0x0a \fBGTH\fP 0x12 \fBLDR\fP 0x1a \fBMUL\fP + 0x03 \fBNIP\fP 0x0b \fBLTH\fP 0x13 \fBSTR\fP 0x1b \fBDIV\fP + 0x04 \fBSWP\fP 0x0c \fBJMP\fP 0x14 \fBLDA\fP 0x1c \fBAND\fP + 0x05 \fBROT\fP 0x0d \fBJCN\fP 0x15 \fBSTA\fP 0x1d \fBORA\fP + 0x06 \fBDUP\fP 0x0e \fBJSR\fP 0x16 \fBDEI\fP 0x1e \fBEOR\fP + 0x07 \fBOVR\fP 0x0f \fBSTH\fP 0x17 \fBDEO\fP 0x1f \fBSFT\fP + +The "complete" opcode's value can be derived by combining the base value with its flags. + +For example, \fBADD2k\fP is \fB(ADD | 2 | k)\fP = \fB(0x18 | 0x20 | 0x80)\fP = \fB0xb8\fP. + +Unlike other opcodes, \fB0x00\fP (\fBBRK*\fP) is contextual: its meaning depends on the \fImode\fP bits provided: + + 0x00 \fBBRK\fP 0x80 \fBLIT\fP + 0x20 \fBJCI\fP 0xa0 \fBLIT2\fP + 0x40 \fBJMI\fP 0xc0 \fBLITr\fP + 0x60 \fBJSI\fP 0xe0 \fBLIT2r\fP + +.SH STACK EFFECTS + +.BR + +.SS NOTATION + +Given a stack effect \fB( a^ b^ c^ -- c^ a^ b^ )\fP here is what each symbol means: + + \fB(\fP and \fB)\fP are comment delimiters + \fBa^\fP, \fBb^\fP, and \fBc^\fP are values on the stack + \fB^\fP indicates that each value is a \fIbyte\fP (\fB*\fP would indicate \fIshort\fP) + \fB--\fP separates the "before" and "after" of the stack effect + +The effect here is to move the top byte of the stack below the next two bytes, which could be achieved with \fBROT ROT\fP. + +By default stack effects describe the effect on \fBwst\fP. When \fBrst\fP is involved we use \fB[]\fP to differentiate the stacks. For example \fB( a* [b*] -- a+1* [b+1*] )\fP will increment the top short of both \fBwst\fP and \fBrst\fP. + +.SS EFFECTS AND MODES + +Regular instructions have a single stack effect which is modified in a predictable way by any additional modes. + +For example the generic effect for \fBADD\fP is ( x y -- x+y ). The eight combinations of modes have the following effects: + + \fBADD\fP ( x^ y^ -- x+y^ ) sum two bytes using \fBwst\fP + \fBADDr\fP ( [x^ y^] -- [x+y^] ) sum two bytes using \fBrst\fP + \fBADD2\fP ( x* y* -- x+y* ) sum two shorts using \fBwst\fP + \fBADD2r\fP ( [x* y*] -- [x+y*] ) sum two shorts using \fBrst\fP + \fBADDk\fP ( x^ y^ -- x^ y^ x+y^ ) sum two bytes using \fBwst\fP, retain arguments + \fBADDkr\fP ( [x^ y^] -- [x^ y^ x+y^] ) sum two bytes using \fBrst\fP, retain arguments + \fBADD2k\fP ( x* y* -- x* y* x+y* ) sum two shorts using \fBwst\fP, retain arguments + \fBADD2kr\fP ( [x* y*] -- [x* y* x+y*] ) sum two shorts using \fBrst\fP, retain arguments + +Thus for regular instructions writing a "generic" effect (leaving sigils off values whose size depends on \fIshort mode\fP) is sufficient to describe its behavior across all eight variations. Note that some instructions always read values of a fixed size. For example the boolean condition read by \fBJCN\fP is always one byte, no matter what modes are used. + +In \fIreturn mode\fP the stacks are reversed. Effects on \fBwst\fP will instead affect \fBrst\fP, and effects on \fBrst\fP will instead affect \fBwst\fP. For example, \fBSTH\fP reads a byte from \fBwst\fP and writes it to \fBrst\fP, but \fBSTHr\fP reads a byte from \fBrst\fP and writes it to \fBwst\fP. + +In \fIkeep mode\fP all the values on the left-hand side of the stack effect will also appear on the right-hand side before the outputs. For example, \fBSWP\fP is \fB(x y -- y x)\fP but \fBSWPk\fP is \fB(x y -- x y y x)\fP. + +.SS TERMINOLOGY + +We consider the top of the stack to be the first value of the stack, and count back from there. For example, given the stack effect \fB( a b c -- )\fP we would say that \fBc\fP is the top of the stack, \fBb\fP is the second value (second from the top), and \fBa\fP is the third value (third from the top). + +.SH REGULAR INSTRUCTIONS + +.BR + +.SS INC +( x -- x+1 ) + +Increment the top value of the stack by 1. + +Overflow will be truncated, so \fB#ff INC\fP will evaluate to \fB0x00\fP. + +.SS POP +( x -- ) + +Remove the top value of the stack. + +\fBPOPk\fP is guaranteed to have no effect (it will not change the stack). + +.SS NIP +( x y -- y ) + +Remove the second value of the stack. + +\fBNIPk\fP is guaranteed to have no effect (it will not change the stack). + +.SS SWP +( x y -- y x ) + +Swap the top two values of the stack. + +.SS ROT +( x y z -- y z x ) + +Rotate the top three values of the stack. The lowest becomes the top and the others are each shifted down one place. + +.SS DUP +( x -- x x ) + +Place a copy of the top value of the stack on top of the stack. + +.SS OVR +( x y -- x y x ) + +Place a copy of the second value of the stack on top of the stack. + +.SS EQU +( x y -- x==y^ ) + +Test whether the top two values of the stack are equal. + +Result is guaranteed to be boolean (\fB0x00\fP or \fB0x01\fP). + +.SS NEQ +( x y -- x!=y^ ) + +Test whether the top two values of the stack are not equal. + +Result is guaranteed to be boolean (\fB0x00\fP or \fB0x01\fP). + +.SS GTH +( x y -- x>y^ ) + +Test whether the second value of the stack is greater than the top. + +Result is guaranteed to be boolean (\fB0x00\fP or \fB0x01\fP). + +.SS LTH +( x y -- x>l)<