A five instruction program that writes one port and exits has no Data Segment at all, and the loader stopped the machine dead on it. It asked the memory controller to move a segment of no bytes, and a length of zero asks for the whole 64K - which is the machine's rule, and a reasonable one, since two bytes cannot say 65536 and a transfer of nothing is not usually what anybody meant. It is exactly what was meant here. 64K did not fit, the controller refused, and the load stopped half done. ON A TERMINAL THAT PRINTS A FAULT WITH AN ADDRESS. Behind a window it is a frozen picture and no reason at all, which is how it was found and is a separate problem from this one. The header says how long each segment is, so the loader knows before it asks. Both bytes are already in hand, so the test costs one OR. Nothing is lost by skipping the transfer: a blit leaves the controller's addresses past whatever it touched, and a blit of nothing would have left them where they already are, which is where the vectors are read from next. Guarded for the code segment too. A program with no code is equally assemblable and would have stopped in exactly the same place. Mode.sbx is the fix's test and a program worth having on its own: forty columns or eighty, whichever the screen is not in, which is what a person wanting Snake drawn twice the size actually needs. Ten instructions and no data, deliberately - it prints its two digits a register at a time rather than from a string, so it stays the smallest shape a loadable program can take. Nothing else on that disk had ever been that shape, which is why nothing had ever tried it. Reported by the user, who wrote the program. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01E2JrLzFvuFX9fgi1LDRjrW
51 lines
1.8 KiB
NASM
51 lines
1.8 KiB
NASM
; Forty columns or eighty, whichever the screen is not in.
|
|
;
|
|
; A machine wakes up in the forty column mode and CosmOS asks for eighty, because that is
|
|
; what its own output was written for. A game is the other way round: Snake on a forty column
|
|
; screen is the same board drawn twice the size, which is what a person sitting in front of
|
|
; it actually wants.
|
|
;
|
|
; ---- The smallest program this system can load ----
|
|
;
|
|
; Ten instructions and NO DATA AT ALL, which is not a curiosity: it is the shape that found
|
|
; a bug in the loader. Every program written for CosmOS until this one had something in its
|
|
; Data Segment, so the loader had never been asked to move a segment of no bytes - and a
|
|
; length of zero asks the memory controller for the whole 64K, which does not fit, which it
|
|
; refused, which stopped the machine in the middle of loading. On a terminal that printed a
|
|
; fault. Behind a window it looked exactly like a hang.
|
|
;
|
|
; So this is kept dataless on purpose. The two digits it prints are put in a register one at
|
|
; a time rather than being a string, which is the only reason it can say anything at all.
|
|
;
|
|
; Written by Anachronaut
|
|
|
|
#Include services.asm
|
|
|
|
#Program
|
|
|
|
#Base 0x4000
|
|
|
|
start:
|
|
INA 0x31 ; Which mode the screen is in now.
|
|
BRA modeWide ; Nought is the forty column one, so go the other way.
|
|
|
|
; Anything else becomes forty, and that deliberately includes bitmap mode. A program that
|
|
; left the screen with no text on it left nowhere to print, so coming back to a mode that
|
|
; has characters in it is more use than refusing.
|
|
RSTA
|
|
OUTA 0x31
|
|
INIA 0x34 ; '4'
|
|
BRI modeSay
|
|
modeWide:
|
|
INIA 0x01
|
|
OUTA 0x31
|
|
INIA 0x38 ; '8'
|
|
modeSay:
|
|
OUTA 0x00
|
|
INIA 0x30 ; '0'
|
|
OUTA 0x00
|
|
INIA 0x0A
|
|
OUTA 0x00
|
|
RSTA
|
|
SWI osExit
|