Update Sphinx docs with v0.14.0 roadmap and fix stale references

Expand roadmap with detailed implementation plans for the next three
features: MBF binary file compatibility (token-stream conversion at
load/save boundary), hardware I/O simulator (portio.c with PIT/speaker/
CGA/joystick port emulation), and DRAW command fixes (M parsing bug,
scale semantics, A rotation, TA/variable substitution). Remove hardware
I/O from known limitations (moving to planned). Fix stale test counts
(64 -> 66) and version string (0.11.0 -> 0.13.0) across docs.
This commit is contained in:
Eremey Valetov
2026-03-11 08:11:13 -04:00
parent 000116b2a2
commit c488cb526d
4 changed files with 72 additions and 12 deletions
+1 -1
View File
@@ -57,7 +57,7 @@ HAL writes straight to stdout.
src/ — core interpreter (21 files)
include/ — headers (13 files)
platform/ — HAL backends (1 file)
tests/ — 64 automated test programs, 4 classic interactive programs, compat harness
tests/ — 66 automated test programs, 4 classic interactive programs, compat harness
docs/ — Sphinx documentation
```
+1 -1
View File
@@ -37,7 +37,7 @@ Running `./gwbasic` with no arguments launches the full-screen editor:
```
$ ./gwbasic
GW-BASIC 2026 0.11.0
GW-BASIC 2026 0.13.0
(C) Eremey Valetov 2026. MIT License.
Based on Microsoft GW-BASIC assembly source.
Ok
+1 -1
View File
@@ -24,7 +24,7 @@ version is structured as modular C suitable for new feature development.
- **Printer output** — `LPRINT`/`LLIST` to file or real hardware via `--lpt`
- **Classic programs** — Hamurabi, Lunar Lander, Gunner, and Diamond from
David Ahl's *BASIC Computer Games* (1978) run out of the box
- **64 test programs** with golden-file regression testing and DOSBox-X
- **66 test programs** with golden-file regression testing and DOSBox-X
compatibility testing against real GWBASIC.EXE
- **MIT License**
+69 -9
View File
@@ -8,15 +8,76 @@
But we've come this far, so why not? Likely approach: translate the token
stream to C and lean on GCC/Clang for the heavy lifting.
## Planned Features
## Next Up (v0.14.0)
- **Hardware I/O simulator** — an optional emulation layer for `OUT`, `INP`,
`WAIT`, `MOTOR`, and friends. The idea is to provide a virtual PC peripheral
bus so retro programs that talk to the speaker, joystick port, or parallel
interface can do *something* useful instead of silently no-oping. Think of it
as a tiny museum exhibit for vintage BASIC hardware hacking.
- **MBF format support for binary LOAD** — convert Microsoft Binary Format
float constants when loading files saved by the original GWBASIC.EXE
### MBF Binary File Compatibility
Make the binary tokenized file format fully compatible with original GWBASIC.EXE
files. Currently, float constants in the token stream are stored as IEEE 754;
the original uses Microsoft Binary Format (MBF).
**Approach:** always store MBF on disk, always IEEE in memory. Convert at the
`load_binary()`/`save_binary()` boundary in `program_io.c`. A token-walking
function scans each line for `TOK_CONST_SNG` (0x1C, 4 bytes) and
`TOK_CONST_DBL` (0x1F, 8 bytes) and converts in-place using the existing
`gw_mbf_to_ieee_*` / `gw_ieee_to_mbf_*` routines. The walker must skip string
literals, REM/DATA regions, and multi-byte tokens to avoid false positives.
This makes round-tripping lossless (MBF single has the same 24-bit mantissa as
IEEE single; MBF double's 56 bits cleanly contain IEEE double's 53 bits) and
enables loading authentic `.BAS` files from the 1980s.
### Hardware I/O Simulator
An optional emulation layer for `OUT`, `INP`, `WAIT`, `MOTOR`, and friends,
following the established `virmem.c` dispatch-by-address pattern.
**New module:** `portio.c` / `portio.h` with `portio_inp(port)` /
`portio_out(port, value)` dispatch.
**Priority ports:**
| Port | Device | Emulation |
|------|--------|-----------|
| 0x420x43 | 8253 PIT channel 2 | Speaker frequency divisor (1193180 / divisor Hz) |
| 0x61 | PPI Port B | Speaker on/off (bits 01), routes to `snd_start_continuous()` / `snd_stop_continuous()` |
| 0x3D8 | CGA mode control | Mode register storage, feeds `gfx_init()` |
| 0x3D9 | CGA color select | Palette/background bits, feeds `gfx_palette_set()` |
| 0x201 | Game port | Joystick stub (returns 0xF0 = no buttons) |
| 0x3F80x3FE | COM1 serial | Minimal stub (LSR reports transmitter ready to prevent spin loops) |
| Default | — | Reads return 0xFF (floating bus), writes silently discarded |
**Statement/function changes:**
- `OUT port, value``portio_out(port, value)`
- `WAIT port, mask [, xor_mask]` → busy loop with `portio_inp()`, break check, timeout
- `MOTOR` → accept and silently ignore
- `INP(port)``portio_inp(port)` (currently returns 0)
- `STICK(n)` / `STRIG(n)` → joystick state from port 0x201
### DRAW Command Fixes
The DRAW mini-language parser has three bugs and four missing features.
**Bugs to fix:**
1. **M command parsing** — the generic argument parser consumes digits that
belong to M's x-coordinate, so `DRAW "M100,50"` moves to (0, 50). Fix:
skip the generic parser when the command is M.
2. **S (scale) semantics** — scale is used as a default distance instead of a
multiplier. `DRAW "U"` moves 4 pixels instead of 1. Correct formula:
`dist = (has_arg ? arg : 1) * scale / 4`.
3. **A (90° rotation)** — recognized but no-op. Needs a rotation state
variable and direction vector transform for U/D/L/R/E/F/G/H.
**Features to add:**
- `TA n` — arbitrary rotation angle (degrees, 360 to 360); requires
multi-character command parsing and trigonometric direction vector rotation
- `=variable;` — numeric variable substitution in DRAW strings; requires
passing variable lookup capability into `gfx_draw()`
- `X subexpr;` — execute sub-string from a string variable (recursive parse)
- Scale applied to relative M coordinates
## IDE and Notebook Integration
@@ -37,4 +98,3 @@
- String garbage collection not implemented (uses `malloc`/`free` instead)
- Maximum 256 variables, 64 arrays, 16 FOR nesting, 24 GOSUB nesting,
16 WHILE nesting
- Hardware I/O (`OUT`, `INP`, `WAIT`, `COM`, `MOTOR`) not yet implemented